using System; using System.Collections.Generic; using System.Linq; using System.Text; using HeuristicLab.Common; using HeuristicLab.Core; using HeuristicLab.Data; using HeuristicLab.Parameters; using HeuristicLab.Persistence.Default.CompositeSerializers.Storable; namespace HeuristicLab.Optimization { [Item("RunCollection Formula Modifier", "Modifies a RunCollection by adding results using the given formula.")] [StorableClass] public class RunCollectionFormulaModifer : ParameterizedNamedItem, IRunCollectionModifier { public override bool CanChangeName { get { return false; } } public override bool CanChangeDescription { get { return false; } } public ValueParameter ResultNameParameter { get { return (ValueParameter)Parameters["ResultName"]; } } public ValueParameter FormulaParameter { get { return (ValueParameter)Parameters["Formula"]; } } #region Construction & Cloning [StorableConstructor] protected RunCollectionFormulaModifer(bool deserializing) : base(deserializing) { } protected RunCollectionFormulaModifer(RunCollectionFormulaModifer original, Cloner cloner) : base(original, cloner) { RegisterEvents(); } public RunCollectionFormulaModifer() { Parameters.Add(new ValueParameter("ResultName", "The name of the result to be generated by this formula.", new StringValue("Calc.Value"))); Parameters.Add(new ValueParameter("Formula", "RPN formula for new value. This can contain existing run parameters or results (optionally in quotes if they contain whitespace), numbers and arithmetic operators in postfix notation.", new StringValue("1 1 +"))); UpdateName(); RegisterEvents(); } public override IDeepCloneable Clone(Cloner cloner) { return new RunCollectionFormulaModifer(this, cloner); } [StorableHook(HookType.AfterDeserialization)] private void AfterDeserialization() { RegisterEvents(); } #endregion private void RegisterEvents() { ResultNameParameter.ToStringChanged += Parameter_NameChanged; FormulaParameter.ToStringChanged += Parameter_NameChanged; } void Parameter_NameChanged(object sender, EventArgs e) { UpdateName(); } private void UpdateName() { name = string.Format("{0} := {1}", ResultNameParameter.Value.Value, FormulaParameter.Value.Value); OnNameChanged(); } public void Modify(List runs) { var calc = new Calculator {Formula = FormulaParameter.Value.Value}; foreach (var run in runs) { var variables = new Dictionary(); foreach (var param in run.Parameters) variables[param.Key] = param.Value; foreach (var result in run.Results) variables[result.Key] = result.Value; run.Results[ResultNameParameter.Value.Value] = calc.GetValue(variables); } } } }