Free cookie consent management tool by TermsFeed Policy Generator

source: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Tracking/Analyzers/SymbolicDataAnalysisSchemaFrequencyAnalyzer.cs @ 13481

Last change on this file since 13481 was 13481, checked in by bburlacu, 8 years ago

#1772: Added schema frequency analyzer, removed unused code from the SymbolicDataAnalysisSubtreeSampleCountAnalyzer

File size: 6.8 KB
Line 
1#region License Information
2/* HeuristicLab
3 * Copyright (C) 2002-2015 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
4 *
5 * This file is part of HeuristicLab.
6 *
7 * HeuristicLab is free software: you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation, either version 3 of the License, or
10 * (at your option) any later version.
11 *
12 * HeuristicLab is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
19 */
20#endregion
21
22using System.Linq;
23using HeuristicLab.Common;
24using HeuristicLab.Core;
25using HeuristicLab.Data;
26using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
27using HeuristicLab.EvolutionTracking;
28using HeuristicLab.Optimization;
29using HeuristicLab.Parameters;
30using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
31
32namespace HeuristicLab.Problems.DataAnalysis.Symbolic.Tracking.Analyzers {
33  [Item("SymbolicDataAnalysisSchemaFrequencyAnalyzer", "An analyzer which counts schema frequencies in the population.")]
34  [StorableClass]
35  public class SymbolicDataAnalysisSchemaFrequencyAnalyzer : EvolutionTrackingAnalyzer<ISymbolicExpressionTree> {
36    private const string MinimumSchemaLengthParameterName = "MinimumSchemaLength";
37
38    [Storable]
39    private readonly SymbolicExpressionTreePhenotypicSimilarityCalculator phenotypicSimilarityCalculator;
40
41    [Storable]
42    private readonly SymbolicExpressionTreeBottomUpSimilarityCalculator genotypicSimilarityCalculator;
43
44    [Storable]
45    private readonly ISymbolicExpressionTreeNodeEqualityComparer comparer;
46    private QueryMatch qm;
47
48    public IFixedValueParameter<IntValue> MinimumSchemaLengthParameter {
49      get { return (IFixedValueParameter<IntValue>)Parameters[MinimumSchemaLengthParameterName]; }
50    }
51
52    public SymbolicDataAnalysisSchemaFrequencyAnalyzer() {
53      comparer = new SymbolicExpressionTreeNodeEqualityComparer {
54        MatchConstantValues = false,
55        MatchVariableNames = true,
56        MatchVariableWeights = false
57      };
58      qm = new QueryMatch(comparer) { MatchParents = true };
59      phenotypicSimilarityCalculator = new SymbolicExpressionTreePhenotypicSimilarityCalculator();
60      genotypicSimilarityCalculator = new SymbolicExpressionTreeBottomUpSimilarityCalculator { SolutionVariableName = "SymbolicExpressionTree" };
61      Parameters.Add(new FixedValueParameter<IntValue>(MinimumSchemaLengthParameterName, new IntValue(10)));
62    }
63
64    protected SymbolicDataAnalysisSchemaFrequencyAnalyzer(SymbolicDataAnalysisSchemaFrequencyAnalyzer original,
65      Cloner cloner) : base(original, cloner) {
66      comparer = original.comparer;
67      phenotypicSimilarityCalculator = original.phenotypicSimilarityCalculator;
68      genotypicSimilarityCalculator = original.genotypicSimilarityCalculator;
69      qm = new QueryMatch(comparer) { MatchParents = true };
70    }
71
72    public override IDeepCloneable Clone(Cloner cloner) {
73      return new SymbolicDataAnalysisSchemaFrequencyAnalyzer(this, cloner);
74    }
75
76    [StorableConstructor]
77    protected SymbolicDataAnalysisSchemaFrequencyAnalyzer(bool deserializing) : base(deserializing) { }
78
79
80    [StorableHook(HookType.AfterDeserialization)]
81    private void AfterDeserialization() {
82      qm = new QueryMatch(comparer) { MatchParents = true };
83    }
84
85    public override IOperation Apply() {
86      int updateInterval = UpdateIntervalParameter.Value.Value;
87      IntValue updateCounter = UpdateCounterParameter.ActualValue;
88      // if counter does not yet exist then initialize it with update interval
89      // to make sure the solutions are analyzed on the first application of this operator
90      if (updateCounter == null) {
91        updateCounter = new IntValue(updateInterval);
92        UpdateCounterParameter.ActualValue = updateCounter;
93      }
94      //analyze solutions only every 'updateInterval' times
95      if (updateCounter.Value != updateInterval) {
96        updateCounter.Value++;
97        return base.Apply();
98      }
99      updateCounter.Value = 1;
100
101      if (PopulationGraph == null || Generation.Value == 0)
102        return base.Apply();
103
104      var minimumSchemaLength = MinimumSchemaLengthParameter.Value.Value;
105      var vertices = PopulationGraph.GetByRank(Generation.Value).Cast<IGenealogyGraphNode<ISymbolicExpressionTree>>().ToList();
106      var formatter = new SymbolicExpressionTreeStringFormatter { Indent = false, AppendNewLines = false };
107
108      var schemas = SchemaCreator.GenerateSchemas(vertices, minimumSchemaLength).ToList();
109      var trees = vertices.Select(x => x.Data).ToList();
110      var qualities = vertices.Select(x => x.Quality).ToList();
111      var scopes = ExecutionContext.Scope.SubScopes; // the scopes of all the individuals, needed because the tree evaluated values are stored in the scope and we use them for the phenotypic similarity
112
113      var matrix = new DoubleMatrix(schemas.Count, 5) {
114        RowNames = schemas.Select(x => formatter.Format(x.Root.GetSubtree(0).GetSubtree(0))),
115        ColumnNames = new[] { "Avg. Length", "Avg. Quality", "Relative Frequency", "Avg. Phen. Sim.", "Avg. Gen. Sim" },
116        SortableView = true
117      };
118
119      for (int i = 0; i < schemas.Count; ++i) {
120        var schema = schemas[i];
121        int count = 0;
122        double avgLength = 0;
123        double avgQuality = 0;
124        var matchingScopes = new ScopeList();
125        for (int j = 0; j < trees.Count; ++j) {
126          var tree = trees[j];
127          if (qm.Match(tree, schema)) {
128            count++;
129            avgLength += tree.Length;
130            avgQuality += qualities[j];
131            matchingScopes.Add(scopes[j]);
132          }
133        }
134        avgLength /= count;
135        avgQuality /= count;
136        double relativeFreq = (double)count / trees.Count;
137        double avgPhenotypicSimilarity = SchemaEvaluator.CalculateSimilarity(matchingScopes, phenotypicSimilarityCalculator, true, 4);
138        double avgGenotypicSimilarity = SchemaEvaluator.CalculateSimilarity(matchingScopes, genotypicSimilarityCalculator, true, 4);
139
140        matrix[i, 0] = avgLength;
141        matrix[i, 1] = avgQuality;
142        matrix[i, 2] = relativeFreq;
143        matrix[i, 3] = avgPhenotypicSimilarity;
144        matrix[i, 4] = avgGenotypicSimilarity;
145      }
146
147      if (Results.ContainsKey("Schema Frequencies")) {
148        var result = Results["Schema Frequencies"];
149        result.Value = matrix;
150      } else {
151        var result = new Result("Schema Frequencies", matrix);
152        Results.Add(result);
153      }
154
155      return base.Apply();
156    }
157  }
158}
Note: See TracBrowser for help on using the repository browser.