Free cookie consent management tool by TermsFeed Policy Generator

source: branches/DataAnalysis/HeuristicLab.Problems.DataAnalysis/3.3/Operators/DynOpEqHistogramInitializer.cs @ 5265

Last change on this file since 5265 was 5265, checked in by gkronber, 14 years ago

changed project files and solution file to make the branch compatible with current trunk version. #1142

File size: 9.1 KB
Line 
1#region License Information
2/* HeuristicLab
3 * Copyright (C) 2002-2010 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;
23using System.Linq;
24using HeuristicLab.Core;
25using HeuristicLab.Data;
26using HeuristicLab.Operators;
27using HeuristicLab.Optimization;
28using HeuristicLab.Parameters;
29using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
30using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
31using System.Collections.Generic;
32
33namespace HeuristicLab.Problems.DataAnalysis.Operators {
34  [Item("DynOpEqHistogramInitializer", "Dynamic Operator Equalization Histogram Initializer.")]
35  [StorableClass]
36  public class DynOpEqHistogramInitializer : SingleSuccessorOperator {
37    public ILookupParameter<ItemList<IntValue>> BinCapacityParameter {
38      get { return (ILookupParameter<ItemList<IntValue>>)Parameters["BinCapacity"]; }
39    }
40    public ILookupParameter<ItemList<ItemList<DoubleValue>>> AcceptedBinQualitiesParameter {
41      get { return (ILookupParameter<ItemList<ItemList<DoubleValue>>>)Parameters["AcceptedBinQualities"]; }
42    }
43    public ILookupParameter<IntValue> PopulationSizeParameter {
44      get { return (ILookupParameter<IntValue>)Parameters["PopulationSize"]; }
45    }
46    public IScopeTreeLookupParameter<SymbolicExpressionTree> SymbolicExpressionTreeParameter {
47      get { return (IScopeTreeLookupParameter<SymbolicExpressionTree>)Parameters["SymbolicExpressionTree"]; }
48    }
49    public IScopeTreeLookupParameter<DoubleValue> QualityParameter {
50      get { return (IScopeTreeLookupParameter<DoubleValue>)Parameters["Quality"]; }
51    }
52    public ILookupParameter BinSizeParameter {
53      get { return (ILookupParameter<IntValue>)Parameters["BinSize"]; }
54    }
55    public ILookupParameter<ItemList<IntValue>> AcceptedCountsParameter {
56      get { return (ILookupParameter<ItemList<IntValue>>)Parameters["AcceptedCounts"]; }
57    }
58    public ILookupParameter<ItemList<IntValue>> TotalCountsParameter {
59      get { return (ILookupParameter<ItemList<IntValue>>)Parameters["TotalCounts"]; }
60    }
61    public ILookupParameter<BoolValue> MaximizationParameter {
62      get { return (ILookupParameter<BoolValue>)Parameters["Maximization"]; }
63    }
64
65    public DynOpEqHistogramInitializer()
66      : base() {
67      Parameters.Add(new ScopeTreeLookupParameter<SymbolicExpressionTree>("SymbolicExpressionTree"));
68      Parameters.Add(new ScopeTreeLookupParameter<DoubleValue>("Quality"));
69      Parameters.Add(new LookupParameter<IntValue>("PopulationSize"));
70      Parameters.Add(new ValueLookupParameter<IntValue>("BinSize", new IntValue(5)));
71      Parameters.Add(new LookupParameter<ItemList<IntValue>>("BinCapacity"));
72      Parameters.Add(new LookupParameter<ItemList<ItemList<DoubleValue>>>("AcceptedBinQualities"));
73      Parameters.Add(new LookupParameter<ItemList<IntValue>>("AcceptedCounts"));
74      Parameters.Add(new LookupParameter<ItemList<IntValue>>("TotalCounts"));
75      Parameters.Add(new LookupParameter<BoolValue>("Maximization"));
76    }
77
78    public override IOperation Apply() {
79      if (BinCapacityParameter.ActualValue == null) {
80        InitDefaultCapacityHistogram();
81      } else {
82        ItemList<ItemList<DoubleValue>> acceptedBinQualities = AcceptedBinQualitiesParameter.ActualValue;
83        ItemList<IntValue> acceptedCounts = AcceptedCountsParameter.ActualValue;
84        ItemList<IntValue> totalCounts = TotalCountsParameter.ActualValue;
85
86        int popSize = PopulationSizeParameter.ActualValue.Value;
87
88        ScaleBinQualities(acceptedBinQualities, 0, 1, MaximizationParameter.ActualValue.Value);
89
90        double avgQualitySum = (from binAccepted in acceptedBinQualities
91                                where binAccepted.Count > 0
92                                select (from quality in binAccepted
93                                        select quality.Value).Average())
94                                      .Sum();
95        ItemList<IntValue> binCapacity = BinCapacityParameter.ActualValue;
96        int totalCapacity = 0;
97        for (int i = 0; i < binCapacity.Count; i++) {
98          double avgBinQuality = (from quality in acceptedBinQualities[i]
99                                  select quality.Value)
100                                 .DefaultIfEmpty(0.0)
101                                 .Average();
102
103          binCapacity[i].Value = Math.Max(1, (int)Math.Round(popSize * (avgBinQuality / avgQualitySum)));
104          // rounding can lead to loss of capacity
105          // this is problematic if the bin capacities are strict
106          totalCapacity += binCapacity[i].Value;
107          acceptedBinQualities[i].Clear();
108          acceptedCounts[i].Value = 0;
109        }
110        // distribute the remaining slots starting with the largest bins
111        IEnumerator<IntValue> orderedBinCapacities = binCapacity.OrderBy(x => -x.Value).GetEnumerator();
112
113        while (totalCapacity < popSize & orderedBinCapacities.MoveNext()) {
114          orderedBinCapacities.Current.Value = orderedBinCapacities.Current.Value + 1;
115          totalCapacity++;
116        }
117        if (totalCapacity < popSize) throw new InvalidProgramException("The sum of bin capacities doesn't match the population size");
118        for (int i = 0; i < totalCounts.Count; i++)
119          totalCounts[i].Value = 0;
120      }
121      return base.Apply();
122    }
123
124    public static void ScaleBinQualities(ItemList<ItemList<DoubleValue>> acceptedBinQualities, double min, double max, bool maximization) {
125      double minValue = (from bin in acceptedBinQualities
126                         from value in bin
127                         select value.Value).Min();
128      double maxValue = (from bin in acceptedBinQualities
129                         from value in bin
130                         select value.Value).Max();
131
132      if (!maximization) {
133        double tmp = minValue;
134        minValue = maxValue;
135        maxValue = tmp;
136      }
137
138      double valuesRange = maxValue - minValue;
139      double targetRange = max - min;
140
141      foreach (var bin in acceptedBinQualities) {
142        foreach (var value in bin) {
143          double unitScaledValue = (value.Value - minValue) / valuesRange;
144          double targetScaledValue = unitScaledValue * targetRange + min;
145          value.Value = targetScaledValue;
146        }
147      }
148    }
149
150    private void InitDefaultCapacityHistogram() {
151      ItemArray<SymbolicExpressionTree> trees = SymbolicExpressionTreeParameter.ActualValue;
152      ItemArray<DoubleValue> quality = QualityParameter.ActualValue;
153      var binCapacities = new ItemList<IntValue>();
154      var acceptedQuality = new ItemList<ItemList<DoubleValue>>(20);
155      var acceptedCounts = new ItemList<IntValue>();
156      var totalCounts = new ItemList<IntValue>();
157      BinCapacityParameter.ActualValue = binCapacities;
158      AcceptedBinQualitiesParameter.ActualValue = acceptedQuality;
159      TotalCountsParameter.ActualValue = totalCounts;
160      AcceptedCountsParameter.ActualValue = acceptedCounts;
161      for (int i = 0; i < trees.Length; i++) {
162        int binIndex = GetBinIndexForSize(trees[i].Size);
163        if (Exists(binIndex)) {
164          AddToBin(binIndex, quality[i].Value);
165        } else {
166          CreateNewBin(binIndex);
167        }
168      }
169    }
170
171    private void CreateNewBin(int binIndex) {
172      ItemList<IntValue> binCapacities = BinCapacityParameter.ActualValue;
173      ItemList<ItemList<DoubleValue>> acceptedQualities = AcceptedBinQualitiesParameter.ActualValue;
174      ItemList<IntValue> acceptedCounts = AcceptedCountsParameter.ActualValue;
175      ItemList<IntValue> totalCounts = TotalCountsParameter.ActualValue;
176      for (int i = binCapacities.Count; i <= binIndex; i++) {
177        binCapacities.Add(new IntValue(1));
178        acceptedQualities.Add(new ItemList<DoubleValue>(10));
179        acceptedCounts.Add(new IntValue(0));
180        totalCounts.Add(new IntValue(0));
181      }
182    }
183
184    private void AddToBin(int binIndex, double quality) {
185      ItemList<IntValue> binCapacity = BinCapacityParameter.ActualValue;
186      binCapacity[binIndex].Value = binCapacity[binIndex].Value + 1;
187    }
188
189    private bool Exists(int binIndex) {
190      // if the bin has a capacity set then it exists
191      ItemList<IntValue> binCapacities = BinCapacityParameter.ActualValue;
192      return binIndex < binCapacities.Count;
193    }
194
195    private int GetBinIndexForSize(int size) {
196      int binSize = ((IntValue)BinSizeParameter.ActualValue).Value;
197      return (int)Math.Floor((size - 3.0) / binSize);
198    }
199  }
200}
Note: See TracBrowser for help on using the repository browser.