public bool SolveSimple(AD.Term equation, AD.Variable[] args, double[,] limits, double[][] seeds) { rResults.Clear(); this.dim = args.Length; this.limits = limits; this.ranges = new double[dim]; for (int i = 0; i < dim; i++) { this.ranges[i] = (this.limits[i, 1] - this.limits[i, 0]); } equation = equation.AggregateConstants(); term = AD.TermUtils.Compile(equation, args); this.rpropStepWidth = new double[dim]; this.rpropStepConvergenceThreshold = new double[dim]; if (seeds != null) { for (int i = 0; i < seeds.Length; i++) { RpropResult r = RPropLoopSimple(seeds[i]); rResults.Add(r); if (r.finalUtil > 0.75) { return(true); } } } int runs = 2 * dim - (seeds == null?0:seeds.Length); for (int i = 0; i < runs; i++) { RpropResult r = RPropLoopSimple(null); rResults.Add(r); if (r.finalUtil > 0.75) { return(true); } } int adit = 0; while (!EvalResults() && adit++ < 20) { RpropResult r = RPropLoopSimple(null); rResults.Add(r); if (r.finalUtil > 0.75) { return(true); } } if (adit > 20) { Console.WriteLine("Failed to satisfy heuristic!"); } return(false); }
public double[] SolveTest(AD.Term equation, AD.Variable[] args, double[,] limits) { #if (GSOLVER_LOG) InitLog(); #endif rResults.Clear(); double[] res = null; this.dim = args.Length; this.limits = limits; this.ranges = new double[dim]; for (int i = 0; i < dim; i++) { this.ranges[i] = (this.limits[i, 1] - this.limits[i, 0]); } term = AD.TermUtils.Compile(equation, args); this.rpropStepWidth = new double[dim]; this.samplePoint = new double[dim]; this.Runs = 1; //this.Runs = 0; this.FEvals = 0; //int runs = 1000000; RpropResult rfirst = RPropLoop(null, false, true); if (rfirst.finalUtil > 0.75) { res = rfirst.finalValue; } else { while (true) { this.Runs++; //RpropResult r = RPropLoopSimple(null); RpropResult r = RPropLoop(null, false, false); //Console.WriteLine("Run: {0} Util: {1}",i,r.finalUtil); /*for(int k=0; k<dim; k++) { * Console.Write("{0}\t",r.finalValue[k]); * } * Console.WriteLine();*/ if (r.finalUtil > 0.75) { res = r.finalValue; break; } } } #if (GSOLVER_LOG) CloseLog(); #endif return(res); }
public double[] SolveTest(AD.Term equation, AD.Variable[] args, double[,] limits, int maxRuns, out bool found) { #if (GSOLVER_LOG) InitLog(); #endif found = false; rResults.Clear(); double[] res = null; this.dim = args.Length; this.limits = limits; this.ranges = new double[dim]; for (int i = 0; i < dim; i++) { this.ranges[i] = (this.limits[i, 1] - this.limits[i, 0]); } term = AD.TermUtils.Compile(equation, args); this.rpropStepWidth = new double[dim]; this.rpropStepConvergenceThreshold = new double[dim]; this.Runs = 0; this.FEvals = 0; while (this.Runs < maxRuns) { this.Runs++; //RpropResult r = RPropLoopSimple(null); RpropResult r = RPropLoop(null, false); //Console.WriteLine("Run: {0} Util: {1}",i,r.finalUtil); /*for(int k=0; k<dim; k++) { * Console.Write("{0}\t",r.finalValue[k]); * } * Console.WriteLine();*/ if (r.finalUtil > 0.75) { res = r.finalValue; found = true; break; } } #if (GSOLVER_LOG) CloseLog(); #endif return(res); }
private static bool TryTransformToAutoDiff(ISymbolicExpressionTreeNode node, List <AutoDiff.Variable> variables, List <AutoDiff.Variable> parameters, List <string> variableNames, bool updateVariableWeights, out AutoDiff.Term term) { if (node.Symbol is Constant) { var var = new AutoDiff.Variable(); variables.Add(var); term = var; return(true); } if (node.Symbol is Variable) { var varNode = node as VariableTreeNode; var par = new AutoDiff.Variable(); parameters.Add(par); variableNames.Add(varNode.VariableName); if (updateVariableWeights) { var w = new AutoDiff.Variable(); variables.Add(w); term = AutoDiff.TermBuilder.Product(w, par); } else { term = par; } return(true); } if (node.Symbol is Addition) { List <AutoDiff.Term> terms = new List <Term>(); foreach (var subTree in node.Subtrees) { AutoDiff.Term t; if (!TryTransformToAutoDiff(subTree, variables, parameters, variableNames, updateVariableWeights, out t)) { term = null; return(false); } terms.Add(t); } term = AutoDiff.TermBuilder.Sum(terms); return(true); } if (node.Symbol is Subtraction) { List <AutoDiff.Term> terms = new List <Term>(); for (int i = 0; i < node.SubtreeCount; i++) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(i), variables, parameters, variableNames, updateVariableWeights, out t)) { term = null; return(false); } if (i > 0) { t = -t; } terms.Add(t); } if (terms.Count == 1) { term = -terms[0]; } else { term = AutoDiff.TermBuilder.Sum(terms); } return(true); } if (node.Symbol is Multiplication) { List <AutoDiff.Term> terms = new List <Term>(); foreach (var subTree in node.Subtrees) { AutoDiff.Term t; if (!TryTransformToAutoDiff(subTree, variables, parameters, variableNames, updateVariableWeights, out t)) { term = null; return(false); } terms.Add(t); } if (terms.Count == 1) { term = terms[0]; } else { term = terms.Aggregate((a, b) => new AutoDiff.Product(a, b)); } return(true); } if (node.Symbol is Division) { List <AutoDiff.Term> terms = new List <Term>(); foreach (var subTree in node.Subtrees) { AutoDiff.Term t; if (!TryTransformToAutoDiff(subTree, variables, parameters, variableNames, updateVariableWeights, out t)) { term = null; return(false); } terms.Add(t); } if (terms.Count == 1) { term = 1.0 / terms[0]; } else { term = terms.Aggregate((a, b) => new AutoDiff.Product(a, 1.0 / b)); } return(true); } if (node.Symbol is Logarithm) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, updateVariableWeights, out t)) { term = null; return(false); } else { term = AutoDiff.TermBuilder.Log(t); return(true); } } if (node.Symbol is Exponential) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, updateVariableWeights, out t)) { term = null; return(false); } else { term = AutoDiff.TermBuilder.Exp(t); return(true); } } if (node.Symbol is Square) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, updateVariableWeights, out t)) { term = null; return(false); } else { term = AutoDiff.TermBuilder.Power(t, 2.0); return(true); } } if (node.Symbol is SquareRoot) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, updateVariableWeights, out t)) { term = null; return(false); } else { term = AutoDiff.TermBuilder.Power(t, 0.5); return(true); } } if (node.Symbol is Sine) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, updateVariableWeights, out t)) { term = null; return(false); } else { term = sin(t); return(true); } } if (node.Symbol is Cosine) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, updateVariableWeights, out t)) { term = null; return(false); } else { term = cos(t); return(true); } } if (node.Symbol is Tangent) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, updateVariableWeights, out t)) { term = null; return(false); } else { term = tan(t); return(true); } } if (node.Symbol is Erf) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, updateVariableWeights, out t)) { term = null; return(false); } else { term = erf(t); return(true); } } if (node.Symbol is Norm) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, updateVariableWeights, out t)) { term = null; return(false); } else { term = norm(t); return(true); } } if (node.Symbol is StartSymbol) { var alpha = new AutoDiff.Variable(); var beta = new AutoDiff.Variable(); variables.Add(beta); variables.Add(alpha); AutoDiff.Term branchTerm; if (TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, updateVariableWeights, out branchTerm)) { term = branchTerm * alpha + beta; return(true); } else { term = null; return(false); } } term = null; return(false); }
public double[] Solve(AD.Term equation, AD.Variable[] args, double[,] limits, double[][] seeds, double sufficientUtility, out double util) { this.FEvals = 0; this.Runs = 0; util = 0; this.utilityThreshold = sufficientUtility; #if (GSOLVER_LOG) InitLog(); #endif rResults.Clear(); ulong begin = RosCS.RosSharp.Now(); this.dim = args.Length; this.limits = limits; this.ranges = new double[dim]; for (int i = 0; i < dim; i++) { this.ranges[i] = (this.limits[i, 1] - this.limits[i, 0]); } #if AGGREGATE_CONSTANTS equation = equation.AggregateConstants(); #endif term = AD.TermUtils.Compile(equation, args); AD.ConstraintUtility cu = (AD.ConstraintUtility)equation; bool utilIsConstant = (cu.Utility is AD.Constant); if (utilIsConstant) { this.utilityThreshold = 0.75; } bool constraintIsConstant = (cu.Constraint is AD.Constant); if (constraintIsConstant) { if (((AD.Constant)cu.Constraint).Value < 0.25) { util = ((AD.Constant)cu.Constraint).Value; double[] ret = new double[dim]; for (int i = 0; i < dim; i++) { ret[i] = this.ranges[i] / 2.0 + this.limits[i, 0]; } return(ret); } } //Optimize given seeds this.rpropStepWidth = new double[dim]; this.rpropStepConvergenceThreshold = new double[dim]; if (seeds != null) { this.Runs++; //Run with prefered cached seed RpropResult rpfirst = RPropLoop(seeds[0], true); if (rpfirst.finalUtil > this.utilityThreshold) { util = rpfirst.finalUtil; //Console.WriteLine("FEvals: {0}",this.FEvals); return(rpfirst.finalValue); } rResults.Add(rpfirst); //run with seeds of all other agends for (int i = 1; i < seeds.Length; i++) { if (begin + this.maxSolveTime < RosCS.RosSharp.Now() || this.FEvals > this.MaxFEvals) { break; //do not check any further seeds } this.Runs++; RpropResult rp = RPropLoop(seeds[i], false); if (rp.finalUtil > this.utilityThreshold) { util = rp.finalUtil; //Console.WriteLine("FEvals: {0}",this.FEvals); return(rp.finalValue); } rResults.Add(rp); } } //Here: Ignore all constraints search optimum if (begin + this.maxSolveTime > RosCS.RosSharp.Now() && this.FEvals < this.MaxFEvals) { //if time allows, do an unconstrained run if (!constraintIsConstant && !utilIsConstant && seedWithUtilOptimum) { AD.ICompiledTerm curProb = term; term = AD.TermUtils.Compile(((AD.ConstraintUtility)equation).Utility, args); this.Runs++; double[] utilitySeed = RPropLoop(null).finalValue; term = curProb; //Take result and search with constraints RpropResult ru = RPropLoop(utilitySeed, false); /*if (ru.finalUtil > this.utilityThreshold) { * util = ru.finalUtil; * return ru.finalValue; * }*/ rResults.Add(ru); } } do //Do runs until termination criteria, running out of time, or too many function evaluations { this.Runs++; RpropResult rp = RPropLoop(null, false); if (rp.finalUtil > this.utilityThreshold) { util = rp.finalUtil; //Console.WriteLine("FEvals: {0}",this.FEvals); return(rp.finalValue); } rResults.Add(rp); } while(begin + this.maxSolveTime > RosCS.RosSharp.Now() && this.FEvals < this.MaxFEvals); //return best result int resIdx = 0; RpropResult res = rResults[0]; for (int i = 1; i < rResults.Count; i++) { if (Double.IsNaN(res.finalUtil) || rResults[i].finalUtil > res.finalUtil) { if (resIdx == 0 && seeds != null && !Double.IsNaN(res.finalUtil)) { if (rResults[i].finalUtil - res.finalUtil > utilitySignificanceThreshold && rResults[i].finalUtil > 0.75) { res = rResults[i]; resIdx = i; } } else { res = rResults[i]; resIdx = i; } } } //Console.WriteLine("ResultIndex: {0} Delta {1}",resIdx,res.finalUtil-rResults[0].finalUtil); #if (GSOLVER_LOG) CloseLog(); #endif // Console.Write("Found: "); // for(int i=0; i<dim; i++) { // Console.Write("{0}\t",res.finalValue[i]); // } // Console.WriteLine(); // //Console.WriteLine("Runs: {0} FEvals: {1}",this.Runs,this.FEvals); util = res.finalUtil; return(res.finalValue); }
public bool SolveSimple(AD.Term equation, AD.Variable[] args, double[,] limits) { return(SolveSimple(equation, args, limits, null)); }
public double[] Solve(AD.Term equation, AD.Variable[] args, double[,] limits, out double util) { return(Solve(equation, args, limits, null, Double.MaxValue, out util)); }
private static bool TryTransformToAutoDiff(ISymbolicExpressionTreeNode node, List <AutoDiff.Variable> variables, List <AutoDiff.Variable> parameters, List <string> variableNames, out AutoDiff.Term term) { if (node.Symbol is Constant) { var var = new AutoDiff.Variable(); variables.Add(var); term = var; return(true); } if (node.Symbol is Variable) { var varNode = node as VariableTreeNode; var par = new AutoDiff.Variable(); parameters.Add(par); variableNames.Add(varNode.VariableName); var w = new AutoDiff.Variable(); variables.Add(w); term = AutoDiff.TermBuilder.Product(w, par); return(true); } if (node.Symbol is Addition) { List <AutoDiff.Term> terms = new List <Term>(); foreach (var subTree in node.Subtrees) { AutoDiff.Term t; if (!TryTransformToAutoDiff(subTree, variables, parameters, variableNames, out t)) { term = null; return(false); } terms.Add(t); } term = AutoDiff.TermBuilder.Sum(terms); return(true); } if (node.Symbol is Subtraction) { List <AutoDiff.Term> terms = new List <Term>(); for (int i = 0; i < node.SubtreeCount; i++) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(i), variables, parameters, variableNames, out t)) { term = null; return(false); } if (i > 0) { t = -t; } terms.Add(t); } term = AutoDiff.TermBuilder.Sum(terms); return(true); } if (node.Symbol is Multiplication) { AutoDiff.Term a, b; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, out a) || !TryTransformToAutoDiff(node.GetSubtree(1), variables, parameters, variableNames, out b)) { term = null; return(false); } else { List <AutoDiff.Term> factors = new List <Term>(); foreach (var subTree in node.Subtrees.Skip(2)) { AutoDiff.Term f; if (!TryTransformToAutoDiff(subTree, variables, parameters, variableNames, out f)) { term = null; return(false); } factors.Add(f); } term = AutoDiff.TermBuilder.Product(a, b, factors.ToArray()); return(true); } } if (node.Symbol is Division) { // only works for at least two subtrees AutoDiff.Term a, b; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, out a) || !TryTransformToAutoDiff(node.GetSubtree(1), variables, parameters, variableNames, out b)) { term = null; return(false); } else { List <AutoDiff.Term> factors = new List <Term>(); foreach (var subTree in node.Subtrees.Skip(2)) { AutoDiff.Term f; if (!TryTransformToAutoDiff(subTree, variables, parameters, variableNames, out f)) { term = null; return(false); } factors.Add(1.0 / f); } term = AutoDiff.TermBuilder.Product(a, 1.0 / b, factors.ToArray()); return(true); } } if (node.Symbol is Logarithm) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, out t)) { term = null; return(false); } else { term = AutoDiff.TermBuilder.Log(t); return(true); } } if (node.Symbol is Exponential) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, out t)) { term = null; return(false); } else { term = AutoDiff.TermBuilder.Exp(t); return(true); } } if (node.Symbol is Square) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, out t)) { term = null; return(false); } else { term = AutoDiff.TermBuilder.Power(t, 2.0); return(true); } } if (node.Symbol is SquareRoot) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, out t)) { term = null; return(false); } else { term = AutoDiff.TermBuilder.Power(t, 0.5); return(true); } } if (node.Symbol is Sine) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, out t)) { term = null; return(false); } else { term = sin(t); return(true); } } if (node.Symbol is Cosine) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, out t)) { term = null; return(false); } else { term = cos(t); return(true); } } if (node.Symbol is Tangent) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, out t)) { term = null; return(false); } else { term = tan(t); return(true); } } if (node.Symbol is Erf) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, out t)) { term = null; return(false); } else { term = erf(t); return(true); } } if (node.Symbol is Norm) { AutoDiff.Term t; if (!TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, out t)) { term = null; return(false); } else { term = norm(t); return(true); } } if (node.Symbol is StartSymbol) { var alpha = new AutoDiff.Variable(); var beta = new AutoDiff.Variable(); variables.Add(beta); variables.Add(alpha); AutoDiff.Term branchTerm; if (TryTransformToAutoDiff(node.GetSubtree(0), variables, parameters, variableNames, out branchTerm)) { term = branchTerm * alpha + beta; return(true); } else { term = null; return(false); } } term = null; return(false); }
private AutoDiff.Term ConvertToAutoDiff(ISymbolicExpressionTreeNode node) { if (node.Symbol is Constant) { initialConstants.Add(((ConstantTreeNode)node).Value); var var = new AutoDiff.Variable(); variables.Add(var); return(var); } if (node.Symbol is Variable || node.Symbol is BinaryFactorVariable) { var varNode = node as VariableTreeNodeBase; var factorVarNode = node as BinaryFactorVariableTreeNode; // factor variable values are only 0 or 1 and set in x accordingly var varValue = factorVarNode != null ? factorVarNode.VariableValue : string.Empty; var par = FindOrCreateParameter(parameters, varNode.VariableName, varValue); if (makeVariableWeightsVariable) { initialConstants.Add(varNode.Weight); var w = new AutoDiff.Variable(); variables.Add(w); return(AutoDiff.TermBuilder.Product(w, par)); } else { return(varNode.Weight * par); } } if (node.Symbol is FactorVariable) { var factorVarNode = node as FactorVariableTreeNode; var products = new List <Term>(); foreach (var variableValue in factorVarNode.Symbol.GetVariableValues(factorVarNode.VariableName)) { var par = FindOrCreateParameter(parameters, factorVarNode.VariableName, variableValue); initialConstants.Add(factorVarNode.GetValue(variableValue)); var wVar = new AutoDiff.Variable(); variables.Add(wVar); products.Add(AutoDiff.TermBuilder.Product(wVar, par)); } return(AutoDiff.TermBuilder.Sum(products)); } if (node.Symbol is LaggedVariable) { var varNode = node as LaggedVariableTreeNode; var par = FindOrCreateParameter(parameters, varNode.VariableName, string.Empty, varNode.Lag); if (makeVariableWeightsVariable) { initialConstants.Add(varNode.Weight); var w = new AutoDiff.Variable(); variables.Add(w); return(AutoDiff.TermBuilder.Product(w, par)); } else { return(varNode.Weight * par); } } if (node.Symbol is Addition) { List <AutoDiff.Term> terms = new List <Term>(); foreach (var subTree in node.Subtrees) { terms.Add(ConvertToAutoDiff(subTree)); } return(AutoDiff.TermBuilder.Sum(terms)); } if (node.Symbol is Subtraction) { List <AutoDiff.Term> terms = new List <Term>(); for (int i = 0; i < node.SubtreeCount; i++) { AutoDiff.Term t = ConvertToAutoDiff(node.GetSubtree(i)); if (i > 0) { t = -t; } terms.Add(t); } if (terms.Count == 1) { return(-terms[0]); } else { return(AutoDiff.TermBuilder.Sum(terms)); } } if (node.Symbol is Multiplication) { List <AutoDiff.Term> terms = new List <Term>(); foreach (var subTree in node.Subtrees) { terms.Add(ConvertToAutoDiff(subTree)); } if (terms.Count == 1) { return(terms[0]); } else { return(terms.Aggregate((a, b) => new AutoDiff.Product(a, b))); } } if (node.Symbol is Division) { List <AutoDiff.Term> terms = new List <Term>(); foreach (var subTree in node.Subtrees) { terms.Add(ConvertToAutoDiff(subTree)); } if (terms.Count == 1) { return(1.0 / terms[0]); } else { return(terms.Aggregate((a, b) => new AutoDiff.Product(a, 1.0 / b))); } } if (node.Symbol is Absolute) { var x1 = ConvertToAutoDiff(node.GetSubtree(0)); return(abs(x1)); } if (node.Symbol is AnalyticQuotient) { var x1 = ConvertToAutoDiff(node.GetSubtree(0)); var x2 = ConvertToAutoDiff(node.GetSubtree(1)); return(x1 / (TermBuilder.Power(1 + x2 * x2, 0.5))); } if (node.Symbol is Logarithm) { return(AutoDiff.TermBuilder.Log( ConvertToAutoDiff(node.GetSubtree(0)))); } if (node.Symbol is Exponential) { return(AutoDiff.TermBuilder.Exp( ConvertToAutoDiff(node.GetSubtree(0)))); } if (node.Symbol is Square) { return(AutoDiff.TermBuilder.Power( ConvertToAutoDiff(node.GetSubtree(0)), 2.0)); } if (node.Symbol is SquareRoot) { return(AutoDiff.TermBuilder.Power( ConvertToAutoDiff(node.GetSubtree(0)), 0.5)); } if (node.Symbol is Cube) { return(AutoDiff.TermBuilder.Power( ConvertToAutoDiff(node.GetSubtree(0)), 3.0)); } if (node.Symbol is CubeRoot) { return(cbrt(ConvertToAutoDiff(node.GetSubtree(0)))); } if (node.Symbol is Sine) { return(sin( ConvertToAutoDiff(node.GetSubtree(0)))); } if (node.Symbol is Cosine) { return(cos( ConvertToAutoDiff(node.GetSubtree(0)))); } if (node.Symbol is Tangent) { return(tan( ConvertToAutoDiff(node.GetSubtree(0)))); } if (node.Symbol is HyperbolicTangent) { return(tanh( ConvertToAutoDiff(node.GetSubtree(0)))); } if (node.Symbol is Erf) { return(erf( ConvertToAutoDiff(node.GetSubtree(0)))); } if (node.Symbol is Norm) { return(norm( ConvertToAutoDiff(node.GetSubtree(0)))); } if (node.Symbol is StartSymbol) { if (addLinearScalingTerms) { // scaling variables α, β are given at the beginning of the parameter vector var alpha = new AutoDiff.Variable(); var beta = new AutoDiff.Variable(); variables.Add(beta); variables.Add(alpha); var t = ConvertToAutoDiff(node.GetSubtree(0)); return(t * alpha + beta); } else { return(ConvertToAutoDiff(node.GetSubtree(0))); } } throw new ConversionException(); }
public void Compile(Term term) { term.Accept(this); }
public double[] Solve(AD.Term equation, AD.Variable[] args, double[,] limits, double[][] seeds, out double util) { //this.FEvals = 0; util = 0; #if (GSOLVER_LOG) InitLog(); #endif rResults.Clear(); this.dim = args.Length; this.limits = limits; this.ranges = new double[dim]; for (int i = 0; i < dim; i++) { this.ranges[i] = (this.limits[i, 1] - this.limits[i, 0]); } equation = equation.AggregateConstants(); term = AD.TermUtils.Compile(equation, args); AD.ConstraintUtility cu = (AD.ConstraintUtility)equation; bool utilIsConstant = (cu.Utility is AD.Constant); bool constraintIsConstant = (cu.Constraint is AD.Constant); if (constraintIsConstant) { if (((AD.Constant)cu.Constraint).Value < 0.25) { util = ((AD.Constant)cu.Constraint).Value; double[] ret = new double[dim]; for (int i = 0; i < dim; i++) { ret[i] = this.ranges[i] / 2.0 + this.limits[i, 0]; } return(ret); } } this.rpropStepWidth = new double[dim]; this.samplePoint = new double[dim]; if (seeds != null) { RpropResult rpfirst = RPropLoop(seeds[0], true, false); if (utilIsConstant && rpfirst.finalUtil > 0.75) { util = rpfirst.finalUtil; //Console.WriteLine("FEvals: {0}",this.FEvals); return(rpfirst.finalValue); } rResults.Add(rpfirst); for (int i = 1; i < seeds.Length; i++) { RpropResult rp = RPropLoop(seeds[i], false, false); if (utilIsConstant && rp.finalUtil > 0.75) { util = rp.finalUtil; //Console.WriteLine("FEvals: {0}",this.FEvals); return(rp.finalValue); } rResults.Add(rp); } } if (!constraintIsConstant && !utilIsConstant && seedWithUtilOptimum) { AD.ICompiledTerm curProb = term; term = AD.TermUtils.Compile(((AD.ConstraintUtility)equation).Utility, args); double[] utilitySeed = RPropLoop(null).finalValue; /*Console.WriteLine("Unconstraint Seed:"); * Console.Write("S: "); * foreach(double d in utilitySeed) Console.Write("{0} ",d); * Console.WriteLine(); */ term = curProb; rResults.Add(RPropLoop(utilitySeed, false, false)); } int runs = Math.Max(3, 1 * dim - (seeds == null?0:seeds.Length)); //runs = 10; RpropResult rpQS = RPropLoop(null, false, true); if (utilIsConstant && rpQS.finalUtil > 0.75) { util = rpQS.finalUtil; return(rpQS.finalValue); } rResults.Add(rpQS); for (int i = 1; i < runs; i++) { RpropResult rp = RPropLoop(null, false, false); if (utilIsConstant && rp.finalUtil > 0.75) { util = rp.finalUtil; //Console.WriteLine("FEvals: {0}",this.FEvals); return(rp.finalValue); } rResults.Add(rp); } int resIdx = 0; RpropResult res = rResults[0]; for (int i = 1; i < rResults.Count; i++) { if (Double.IsNaN(res.finalUtil) || rResults[i].finalUtil > res.finalUtil) { if (resIdx == 0 && seeds != null && !Double.IsNaN(res.finalUtil)) { if (rResults[i].finalUtil - res.finalUtil > utilitySignificanceThreshold && rResults[i].finalUtil > 0.75) { res = rResults[i]; resIdx = i; } } else { res = rResults[i]; resIdx = i; } } } //Console.WriteLine("ResultIndex: {0} Delta {1}",resIdx,res.finalUtil-rResults[0].finalUtil); #if (GSOLVER_LOG) CloseLog(); #endif // Console.Write("Found: "); // for(int i=0; i<dim; i++) { // Console.Write("{0}\t",res.finalValue[i]); // } // Console.WriteLine(); // //Console.WriteLine("FEvals: {0}",this.FEvals); util = res.finalUtil; return(res.finalValue); }
protected RpropResult RPropOptimizeFeasible(List <CNSAT.Var> constraints, AD.Term ut, AD.Variable[] args, double[] seed, bool precise) { //Compiled Term zusammenbauen AD.Term constr = AD.Term.True; foreach (CNSAT.Var v in constraints) { if (v.Assignment == Alica.Reasoner.CNSAT.Assignment.True) { constr &= v.Term; } else { constr &= ConstraintBuilder.Not(v.Term); } } AD.ConstraintUtility cu = new AD.ConstraintUtility(constr, ut); AD.ICompiledTerm term = AD.TermUtils.Compile(cu, args); Tuple <double[], double> tup; //fertig zusammengebaut runCount++; InitialStepSize(); double[] curGradient; RpropResult ret = new RpropResult(); // curGradient = InitialPoint(constraints, ret); if (seed != null) { curGradient = InitialPointFromSeed(constraints, ret, seed); } else { curGradient = InitialPoint(constraints, ret); } double curUtil = ret.initialUtil; double[] formerGradient = new double[dim]; double[] curValue = new double[dim]; //Tuple<double[],double> tup; Buffer.BlockCopy(ret.initialValue, 0, curValue, 0, sizeof(double) * dim); formerGradient = curGradient; int itcounter = 0; int badcounter = 0; #if (GSOLVER_LOG) Log(curUtil, curValue); #endif int maxIter = 60; int maxBad = 30; double minStep = 1E-11; if (precise) { maxIter = 120; //110 maxBad = 60; //60 minStep = 1E-15; //15 } int convergendDims = 0; while (itcounter++ < maxIter && badcounter < maxBad) { convergendDims = 0; for (int i = 0; i < dim; i++) { if (curGradient[i] * formerGradient[i] > 0) { rpropStepWidth[i] *= 1.3; } else if (curGradient[i] * formerGradient[i] < 0) { rpropStepWidth[i] *= 0.5; } rpropStepWidth[i] = Math.Max(minStep, rpropStepWidth[i]); //rpropStepWidth[i] = Math.Max(0.000001,rpropStepWidth[i]); if (curGradient[i] > 0) { curValue[i] += rpropStepWidth[i]; } else if (curGradient[i] < 0) { curValue[i] -= rpropStepWidth[i]; } if (curValue[i] > limits[i, 1]) { curValue[i] = limits[i, 1]; } else if (curValue[i] < limits[i, 0]) { curValue[i] = limits[i, 0]; } //Console.Write("{0}\t",curValue[i]); if (rpropStepWidth[i] < rpropStepConvergenceThreshold[i]) { ++convergendDims; } } //Abort if all dimensions are converged if (!precise && convergendDims >= dim) { return(ret); } this.fevalsCount++; formerGradient = curGradient; tup = term.Differentiate(curValue); bool allZero = true; for (int i = 0; i < dim; i++) { if (Double.IsNaN(tup.Item1[i])) { ret.aborted = false; //true; //HACK! #if (GSOLVER_LOG) LogStep(); #endif return(ret); } allZero &= (tup.Item1[i] == 0); } curUtil = tup.Item2; formerGradient = curGradient; curGradient = tup.Item1; #if (GSOLVER_LOG) Log(curUtil, curValue); #endif //Console.WriteLine("CurUtil: {0} Final {1}",curUtil,ret.finalUtil); if (curUtil > ret.finalUtil) { badcounter = 0; //Math.Max(0,badcounter-1); ret.finalUtil = curUtil; Buffer.BlockCopy(curValue, 0, ret.finalValue, 0, sizeof(double) * dim); //ret.finalValue = curValue; if (curUtil > 0.75) { return(ret); } } else { badcounter++; } if (allZero) { ret.aborted = false; #if (GSOLVER_LOG) LogStep(); #endif return(ret); } } #if (GSOLVER_LOG) LogStep(); #endif ret.aborted = false; return(ret); }
//Stripped down method for simpler testing public double[] SolveTest(AD.Term equation, AD.Variable[] args, double[,] limits) { lastSeed = null; probeCount = 0; successProbeCount = 0; intervalCount = 0; successIntervalCount = 0; fevalsCount = 0; runCount = 0; //this.FEvals = 0; double util = 0; this.begin = RosCS.RosSharp.Now(); #if (GSOLVER_LOG) InitLog(); #endif //ft.Reset(); rResults.Clear(); currentArgs = args; this.dim = args.Length; this.limits = limits; this.ranges = new double[dim]; this.rpropStepWidth = new double[dim]; this.rpropStepConvergenceThreshold = new double[dim]; equation = equation.AggregateConstants(); ss = new CNSAT.CNSat(); ss.UseIntervalProp = this.UseIntervalProp; //Console.WriteLine(cu.Constraint); LinkedList <CNSAT.Clause> cnf = ft.TransformToCNF(equation, ss); /*Console.WriteLine("Atoms: {0}, Occurrence: {1}",ft.Atoms.Count,ft.AtomOccurrence); * Console.WriteLine("Clauses: {0}",cnf.Count); * foreach(AD.Term atom in ft.Atoms.Keys) { * Console.WriteLine("-------"); * Console.WriteLine(atom); * Console.WriteLine("-------"); * }*/ /* * int litc=1; * List<AD.Term> terms = new List<AD.Term>(ft.Atoms); * * currentAtoms = new Dictionary<int, Term>(); * * foreach(AD.Term t in terms) { * foreach(Literal l in ft.References[t]) { * l.Id = litc; * } * currentAtoms.Add(litc,t); * litc++; * }*/ ip.SetGlobalRanges(args, limits, ss); foreach (CNSAT.Clause c in cnf) { if (!c.IsTautologic) { if (c.Literals.Count == 0) { util = Double.MinValue; double[] ret = new double[dim]; for (int i = 0; i < dim; i++) { ret[i] = (this.limits[i, 1] + this.limits[i, 0]) / 2.0; } return(ret); } //Post Clause Here //Console.Write("\nAdding Clause with "+c.Literals.Count+" Literals\n"); //c.Print(); ss.addBasicClause(c); } } ss.CNSMTGSolver = this; ss.Init(); //PRE-Propagation: #if DO_PREPROPAGATION if (!ip.PrePropagate(ss.Variables)) { Console.WriteLine("Unsatisfiable (unit propagation)"); //return null; } #endif //END-PrePropagation //Console.WriteLine("Variable Count: " + ss.Variables.Count); bool solutionFound = false; solutionFound = ss.solve(); //Console.WriteLine("Solution Found!!!!!"); if (!solutionFound && r1.finalUtil > 0) { r1.finalUtil = -1; } util = r1.finalUtil; //if(util>this.utilitySignificanceThreshold) return r1.finalValue; return(r1.finalValue); }
public double[] Solve(AD.Term equation, AD.Variable[] args, double[,] limits, double[][] seeds, out double util) { lastSeed = null; probeCount = 0; successProbeCount = 0; intervalCount = 0; successIntervalCount = 0; fevalsCount = 0; runCount = 0; this.begin = RosCS.RosSharp.Now(); //this.FEvals = 0; util = 0; #if (GSOLVER_LOG) InitLog(); #endif //ft.Reset(); rResults.Clear(); currentArgs = args; this.dim = args.Length; this.limits = limits; this.ranges = new double[dim]; this.rpropStepWidth = new double[dim]; this.rpropStepConvergenceThreshold = new double[dim]; equation = equation.AggregateConstants(); AD.ConstraintUtility cu = (AD.ConstraintUtility)equation; bool utilIsConstant = (cu.Utility is AD.Constant); bool constraintIsConstant = (cu.Constraint is AD.Constant); if (constraintIsConstant) { if (((AD.Constant)cu.Constraint).Value < 0.25) { util = ((AD.Constant)cu.Constraint).Value; double[] ret = new double[dim]; for (int i = 0; i < dim; i++) { ret[i] = (this.limits[i, 1] + this.limits[i, 0]) / 2.0; //this.ranges[i]/2.0+this.limits[i,0]; } return(ret); } } ss = new CNSAT.CNSat(); ss.UseIntervalProp = this.UseIntervalProp; //Console.WriteLine(cu.Constraint); LinkedList <CNSAT.Clause> cnf = ft.TransformToCNF(cu.Constraint, ss); /*Console.WriteLine("Atoms: {0}, Occurrence: {1}",ft.Atoms.Count,ft.AtomOccurrence); * Console.WriteLine("Clauses: {0}",cnf.Count); * foreach(AD.Term atom in ft.Atoms.Keys) { * Console.WriteLine("-------"); * Console.WriteLine(atom); * Console.WriteLine("-------"); * }*/ /* * int litc=1; * List<AD.Term> terms = new List<AD.Term>(ft.Atoms); * * currentAtoms = new Dictionary<int, Term>(); * * foreach(AD.Term t in terms) { * foreach(Literal l in ft.References[t]) { * l.Id = litc; * } * currentAtoms.Add(litc,t); * litc++; * }*/ if (UseIntervalProp) { ip.SetGlobalRanges(args, limits, ss); } foreach (CNSAT.Clause c in cnf) { if (!c.IsTautologic) { if (c.Literals.Count == 0) { util = Double.MinValue; double[] ret = new double[dim]; for (int i = 0; i < dim; i++) { ret[i] = (this.limits[i, 1] + this.limits[i, 0]) / 2.0; } return(ret); } //Post Clause Here //Console.Write("\nAdding Clause with "+c.Literals.Count+" Literals\n"); //c.Print(); ss.addBasicClause(c); } } ss.CNSMTGSolver = this; ss.Init(); //PRE-Propagation: if (UseIntervalProp) { #if DO_PREPROPAGATION if (!ip.PrePropagate(ss.Variables)) { Console.WriteLine("Unsatisfiable (unit propagation)"); return(null); } #endif } //END-PrePropagation //Console.WriteLine("Variable Count: " + ss.Variables.Count); bool solutionFound = false; ss.UnitDecissions = ss.Decisions.Count; do { if (!solutionFound) { ss.EmptySATClause(); ss.EmptyTClause(); ss.backTrack(ss.UnitDecissions); } solutionFound = ss.solve(); if (Optimize) { r1 = RPropOptimizeFeasible(ss.Decisions, ((AD.ConstraintUtility)equation).Utility, args, r1.finalValue, false); } if (!solutionFound && r1.finalUtil > 0) { r1.finalUtil = -1; } util = r1.finalUtil; if (!Optimize && solutionFound) { return(r1.finalValue); } else if (Optimize) { //optimization case rResults.Add(r1); CNSAT.Clause c = new Alica.Reasoner.CNSAT.Clause(); foreach (CNSAT.Var v in ss.Decisions) { c.Add(new CNSAT.Lit(v, v.Assignment == CNSAT.Assignment.True ? CNSAT.Assignment.False : CNSAT.Assignment.True)); } //ss.addBasicClause(c); ss.addIClause(c); ss.backTrack(ss.Decisions[ss.Decisions.Count - 1].DecisionLevel); solutionFound = false; } } while (!solutionFound && this.begin + this.maxSolveTime > RosCS.RosSharp.Now() /*&& this.runCount < this.MaxFEvals*/); //Console.WriteLine("Probes: {0}/{1}\tIntervals: {2}/{3}",successProbeCount,probeCount,successIntervalCount,intervalCount); //ip.PrintStats(); //Console.WriteLine("Rprop Runs: {0}\t FEvals {1}\t Solutions Found: {2}",this.runCount,this.fevalsCount, rResults.Count); //return best result if (rResults.Count > 0) { foreach (RpropResult rp in rResults) { if (rp.finalUtil > util) { util = rp.finalUtil; r1 = rp; } } return(r1.finalValue); } Console.WriteLine("Unsatisfiable"); return(null); }