package parameterrules; import java.io.*; import main.BetterTokenizer; import main.GeneralInput; import main.MoreMath; import parameters.Parameter; import parameters.ParameterSet; /** Implements the rule that the product of all the input parameters has to lie between lowerBound <= product <= upperBound. */ public class ProductBetweenRule extends ParameterRule { /** These store the lower and upper bounds that the product of the parameters have to be between (inclusive of edges) */ private float lowerBound, upperBound; ProductBetweenRule() {} public float getFuzzyScore(float [] params) { float val = 1f; for(int i = 0; i < numParams; i++) { val *= params[paramNums[i]]; } if(val < lowerBound) return lowerBound - val; else if(val > upperBound) return val - upperBound; else return 0f; } public boolean changeParameters(float [] params, int mode, ParameterSet set) { float val = 1f; // First check if its already good. If so, return true for(int i = 0; i < numParams; i++) { val *= params[paramNums[i]]; } if(val >= lowerBound && val <= upperBound) return true; // Not already good, so randomly pick one value to change int change_param = (int)(MoreMath.random() * numParams); // Take out value we'll change val /= params[paramNums[change_param]]; // Calculate new range float min = lowerBound / val; float max = upperBound / val; // Pick the value pickNewParameterValue(params, paramNums[change_param], min, max, mode, set); return false; } protected void loadParameter(String info, BetterTokenizer tokenizer) throws Exception { if(info.equals("LowerBound")) { GeneralInput.nextToken(tokenizer); lowerBound = (float)tokenizer.nval; } else if(info.equals("UpperBound")) { GeneralInput.nextToken(tokenizer); upperBound = (float)tokenizer.nval; } else super.loadParameter(info, tokenizer); } }