Free cookie consent management tool by TermsFeed Policy Generator

source: branches/2971_named_intervals/HeuristicLab.Problems.DataAnalysis.Symbolic.Regression/3.4/SymbolicRegressionPruningOperator.cs @ 16628

Last change on this file since 16628 was 16628, checked in by gkronber, 5 years ago

#2971: made branch compile with current version of trunk

File size: 5.9 KB
Line 
1#region License Information
2
3/* HeuristicLab
4 * Copyright (C) 2002-2018 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
5 *
6 * This file is part of HeuristicLab.
7 *
8 * HeuristicLab is free software: you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation, either version 3 of the License, or
11 * (at your option) any later version.
12 *
13 * HeuristicLab is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 * GNU General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License
19 * along with HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
20 */
21
22#endregion
23
24using System.Collections.Generic;
25using System.Linq;
26using HeuristicLab.Common;
27using HeuristicLab.Core;
28using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
29using HeuristicLab.Parameters;
30using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
31using HEAL.Attic;
32
33namespace HeuristicLab.Problems.DataAnalysis.Symbolic.Regression {
34  [StorableType("0FEF3C8C-5A49-4E7E-BFD9-C4498E750077")]
35  [Item("SymbolicRegressionPruningOperator", "An operator which prunes symbolic regression trees.")]
36  public class SymbolicRegressionPruningOperator : SymbolicDataAnalysisExpressionPruningOperator {
37    private const string EvaluatorParameterName = "Evaluator";
38
39    #region parameter properties
40    public ILookupParameter<ISymbolicRegressionSingleObjectiveEvaluator> EvaluatorParameter {
41      get { return (ILookupParameter<ISymbolicRegressionSingleObjectiveEvaluator>)Parameters[EvaluatorParameterName]; }
42    }
43    #endregion
44
45    protected SymbolicRegressionPruningOperator(SymbolicRegressionPruningOperator original, Cloner cloner)
46      : base(original, cloner) {
47    }
48    public override IDeepCloneable Clone(Cloner cloner) {
49      return new SymbolicRegressionPruningOperator(this, cloner);
50    }
51
52    [StorableConstructor]
53    protected SymbolicRegressionPruningOperator(StorableConstructorFlag _) : base(_) { }
54
55    public SymbolicRegressionPruningOperator(ISymbolicDataAnalysisSolutionImpactValuesCalculator impactValuesCalculator)
56      : base(impactValuesCalculator) {
57      Parameters.Add(new LookupParameter<ISymbolicRegressionSingleObjectiveEvaluator>(EvaluatorParameterName));
58    }
59
60    [StorableHook(HookType.AfterDeserialization)]
61    private void AfterDeserialization() {
62      // BackwardsCompatibility3.3
63      #region Backwards compatible code, remove with 3.4
64      base.ImpactValuesCalculator = new SymbolicRegressionSolutionImpactValuesCalculator();
65      if (!Parameters.ContainsKey(EvaluatorParameterName)) {
66        Parameters.Add(new LookupParameter<ISymbolicRegressionSingleObjectiveEvaluator>(EvaluatorParameterName));
67      }
68      #endregion
69    }
70
71    protected override ISymbolicDataAnalysisModel CreateModel(ISymbolicExpressionTree tree, ISymbolicDataAnalysisExpressionTreeInterpreter interpreter, IDataAnalysisProblemData problemData, DoubleLimit estimationLimits) {
72      var regressionProblemData = (IRegressionProblemData)problemData;
73      return new SymbolicRegressionModel(regressionProblemData.TargetVariable, tree, interpreter, estimationLimits.Lower, estimationLimits.Upper);
74    }
75
76    protected override double Evaluate(IDataAnalysisModel model) {
77      var regressionModel = (ISymbolicRegressionModel)model;
78      var regressionProblemData = (IRegressionProblemData)ProblemDataParameter.ActualValue;
79      var evaluator = EvaluatorParameter.ActualValue;
80      var fitnessEvaluationPartition = FitnessCalculationPartitionParameter.ActualValue;
81      var rows = Enumerable.Range(fitnessEvaluationPartition.Start, fitnessEvaluationPartition.Size);
82      return evaluator.Evaluate(this.ExecutionContext, regressionModel.SymbolicExpressionTree, regressionProblemData, rows);
83    }
84
85    public static ISymbolicExpressionTree Prune(ISymbolicExpressionTree tree, SymbolicRegressionSolutionImpactValuesCalculator impactValuesCalculator, ISymbolicDataAnalysisExpressionTreeInterpreter interpreter, IRegressionProblemData problemData, DoubleLimit estimationLimits, IEnumerable<int> rows, double nodeImpactThreshold = 0.0, bool pruneOnlyZeroImpactNodes = false) {
86      var clonedTree = (ISymbolicExpressionTree)tree.Clone();
87      var model = new SymbolicRegressionModel(problemData.TargetVariable, clonedTree, interpreter, estimationLimits.Lower, estimationLimits.Upper);
88      var nodes = clonedTree.Root.GetSubtree(0).GetSubtree(0).IterateNodesPrefix().ToList(); // skip the nodes corresponding to the ProgramRootSymbol and the StartSymbol
89
90      double qualityForImpactsCalculation = double.NaN; // pass a NaN value initially so the impact calculator will calculate the quality
91
92      for (int i = 0; i < nodes.Count; ++i) {
93        var node = nodes[i];
94        if (node is ConstantTreeNode) continue;
95
96        double impactValue, replacementValue;
97        double newQualityForImpactsCalculation;
98        impactValuesCalculator.CalculateImpactAndReplacementValues(model, node, problemData, rows, out impactValue, out replacementValue, out newQualityForImpactsCalculation, qualityForImpactsCalculation);
99
100        if (pruneOnlyZeroImpactNodes && !impactValue.IsAlmost(0.0)) continue;
101        if (!pruneOnlyZeroImpactNodes && impactValue > nodeImpactThreshold) continue;
102
103        var constantNode = (ConstantTreeNode)node.Grammar.GetSymbol("Constant").CreateTreeNode();
104        constantNode.Value = replacementValue;
105
106        ReplaceWithConstant(node, constantNode);
107        i += node.GetLength() - 1; // skip subtrees under the node that was folded
108
109        qualityForImpactsCalculation = newQualityForImpactsCalculation;
110      }
111      return model.SymbolicExpressionTree;
112    }
113  }
114}
Note: See TracBrowser for help on using the repository browser.