package stoppers; import java.lang.*; import java.io.*; import main.BetterTokenizer; import java.math.*; import main.Cell; import main.GeneralInput; import main.Model; public class StripeStop extends SimpleStop { int stripeWidth, nonStripeWidth; String node; int fpos= -1, lpos= -1; // left and right bounds of stripe, matches array index float threshold = (float) Math.exp(5.0); // should be exp(sDif) boolean done=false; float interval=1f; // stripe parameters float sMin=0.2f; // higher is better float sDif=5f; // ratio between instripe and exstripe float [] stripeMeans; // No arg constructor for instantiating by name public StripeStop() { stopTime = 1; } public void init(Model model) { super.init(model); stripeMeans = new float[model.arrayWidth]; } public void loadParameters(BetterTokenizer tokenizer) throws Exception { super.loadParameters(tokenizer); if((lpos < 0) || (fpos < 0) || (lpos >= model.arrayWidth) || (fpos >= model.arrayWidth) || (lpos - fpos < 0) || ((lpos - fpos) == (model.arrayWidth - 1))) throw new Exception("Error in StripeStop: Stripe not properly specified"); stripeWidth = (lpos - fpos + 1); nonStripeWidth = model.arrayWidth - stripeWidth; } protected void loadParameter(String info, BetterTokenizer tokenizer) throws Exception { if(info.equals("Node")) { GeneralInput.nextToken(tokenizer); node = tokenizer.sval; } else if(info.equals("LeftStripeBorder")) { GeneralInput.nextToken(tokenizer); fpos = ((int)tokenizer.nval-1); } // subtract 1 to make pos an array index else if(info.equals("RightStripeBorder")) { GeneralInput.nextToken(tokenizer); lpos = ((int)tokenizer.nval-1); } // subtract 1 to make pos an array index else if(info.equals("Interval")) { GeneralInput.nextToken(tokenizer); interval = (float)tokenizer.nval; } else if(info.equals("StripeThreshold")) { GeneralInput.nextToken(tokenizer); sMin = (float)tokenizer.nval; } else if(info.equals("StripeDifference")) { GeneralInput.nextToken(tokenizer); sDif = (float)tokenizer.nval; threshold = (float) Math.exp((double) sDif); } else super.loadParameter(info,tokenizer); } public boolean stop(float time) { float instripe=0, exstripe=0; for(int i = 0; i < model.arrayWidth; i++) stripeMeans[i] = 0; if(time > 0) // time < 0 means MetaStopper's controlling things if(time < lastTime + interval) { return false; } if(done) return true; if(time > stopTime) return done=true; for(int i = 0; i< model.arrayHeight; i++) { int pos = i*model.arrayWidth; for(int j = 0; j < model.arrayWidth; j++) stripeMeans[j] += model.cells[pos + j].nodePeek(node); } for(int j = 0; j < fpos; j++) exstripe += stripeMeans[j]; for(int j = fpos; j <= lpos; j++) instripe += stripeMeans[j] - sMin; for(int j = lpos + 1; j < model.arrayWidth; j++) exstripe += stripeMeans[j]; instripe = instripe/stripeWidth; exstripe = exstripe/nonStripeWidth; score = (float) Math.exp((double) (instripe/exstripe)); cumScore += score * (time - lastTime); lastTime = time; if(score < threshold) { score = -cumScore; // this is really (cumScore/totalTime) * totalTime return true; } else return false; } public void initCells() { for(int col = fpos; col <= lpos; col++) { for(int row = 0; row < model.arrayHeight; row++) { try { model.cells[row * model.arrayWidth + col].setValue(node, 1f); // set each column full on } catch(Exception e) { System.out.println(e.toString()); } } } } }