Free cookie consent management tool by TermsFeed Policy Generator

source: branches/2988_ModelsOfModels2/HeuristicLab.Algorithms.EMM/EMMAlgorithm.cs @ 16811

Last change on this file since 16811 was 16760, checked in by msemenki, 6 years ago

#2988: ADD:

  1. new type of mutation that respect node type and do not change trigonometric node to "add" node;
  2. variation of previous mutation type that do not change type of terminal node;
  3. some interface adjusting for comfort work with algorithm;
  4. second variant of map, that is not "island" map but provide "net" map.
File size: 13.6 KB
RevLine 
[16722]1#region License Information
2/* HeuristicLab
3 * Copyright (C) 2002-2019 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 HEAL.Attic;
23using HeuristicLab.Common;
24using HeuristicLab.Core;
25using HeuristicLab.Data;
26using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
27using HeuristicLab.Problems.DataAnalysis.Symbolic;
28using HeuristicLab.Random;
29using HeuristicLab.Selection;
[16760]30using System;
[16722]31using System.Collections.Generic;
32using System.IO;
33using System.Linq;
34using CancellationToken = System.Threading.CancellationToken;
35using Variable = HeuristicLab.Core.Variable;
36
37namespace HeuristicLab.Algorithms.EvolvmentModelsOfModels {
38  [Item("EvolvmentModelsOfModels Algorithm ", "EMM implementation")]
39  [Creatable(CreatableAttribute.Categories.PopulationBasedAlgorithms, Priority = 125)]
[16734]40  [StorableType("AD23B21F-089A-4C6C-AD2E-1B01E7939CF5")]
[16722]41  public class EMMAlgorithm : EvolvmentModelsOfModelsAlgorithmBase {
42    public EMMMapTreeModel Map { get; private set; }
43
44    public EMMAlgorithm() : base() { }
45    protected EMMAlgorithm(EMMAlgorithm original, Cloner cloner) : base(original, cloner) {
46      if (original.Map != null) {
47        Map = cloner.Clone(original.Map);
48      }
49    }
50    public override IDeepCloneable Clone(Cloner cloner) {
51      return new EMMAlgorithm(this, cloner);
52    }
53
54    [StorableConstructor]
55    protected EMMAlgorithm(StorableConstructorFlag _) : base(_) { }
56
57    protected override void Run(CancellationToken cancellationToken) {
58      InfixExpressionParser parser = new InfixExpressionParser();
59      var trees = File.ReadAllLines(InputFileParameter.Value.Value).Select(parser.Parse);
[16734]60      // this.Problem.SymbolicExpressionTreeGrammar;
61      /*   Problem.ProblemData.Dataset.ColumnNames.Take(2).ToList();
62         trees.First().Root.Grammar.ContainsSymbol((IVariable)a).
63           = this.Problem.SymbolicExpressionTreeGrammar;*/
[16760]64      int neghboorNumber = 10;
65      switch (MapCreationType.Value) { // Configure Map type and it's parameters: IslandMap, FullMap and Percent, Number
66        case "IslandMap": break;
67        case "FullMap":
68          ClusterNumbersParameter.Value.Value = trees.Count();
69          switch (NegbourType.Value) {
70            case "Percent": neghboorNumber = Convert.ToInt32((Convert.ToDouble(ClusterNumbersParameter.Value.Value)) * (Convert.ToDouble(NegbourNumber.Value)) / 100.0); break;
71            case "Number": neghboorNumber = NegbourNumber.Value; break;
72            default: neghboorNumber = NegbourNumber.Value; break;
73          }
74          break;
75        default: MapCreationType.Value = "IslandMap"; break;
76      }
77      switch (AlgorithmImplemetationType.Value) { //Configure type of algorithm application
78        case "OnlyMapCreation": // for case when we want only create map, and do  not want made somting also. OnlyMapCreation, CrateMapAndGo, ReadMapAndGo
79          Map = new EMMMapTreeModel(RandomParameter.Value, trees, ClusterNumbersParameter.Value.Value, neghboorNumber);
[16734]80          ClusterNumbersParameter.Value.Value = Map.K;
81          File.WriteAllLines("Map.txt", Map.MapToString());
82          File.WriteAllLines("MapToSee.txt", Map.MapToSee());
83          globalScope = new Scope("Global Scope");
84          executionContext = new ExecutionContext(null, this, globalScope);
85          break;
[16760]86        case "ReadMapAndGo": // for case when we want read existed map and work with it;
[16734]87          Map = new EMMMapTreeModel(RandomParameter.Value, trees);
88          ClusterNumbersParameter.Value.Value = Map.K;
89          if (previousExecutionState != ExecutionState.Paused) {
90            InitializeAlgorithm(cancellationToken);
91          }
92          globalScope.Variables.Add(new Variable("TreeModelMap", Map));
[16760]93          EMMAlgorithmRun(cancellationToken);
[16734]94          break;
[16760]95        case "CreateMapAndGo":
96          Map = new EMMMapTreeModel(RandomParameter.Value, trees, ClusterNumbersParameter.Value.Value, neghboorNumber);
97          ClusterNumbersParameter.Value.Value = Map.K;
98          if (previousExecutionState != ExecutionState.Paused) {
99            InitializeAlgorithm(cancellationToken);
100          }
101          globalScope.Variables.Add(new Variable("TreeModelMap", Map));
102          File.WriteAllLines("Map.txt", Map.MapToString());
103          File.WriteAllLines("MapToSee.txt", Map.MapToSee());
104          EMMAlgorithmRun(cancellationToken);
105          break;
[16734]106        default: //for case of usial from zero step starting
[16760]107          AlgorithmImplemetationType.Value = "CreateMapAndGo";
108          Map = new EMMMapTreeModel(RandomParameter.Value, trees, ClusterNumbersParameter.Value.Value, neghboorNumber);
[16734]109          ClusterNumbersParameter.Value.Value = Map.K;
[16760]110          File.WriteAllLines("Map.txt", Map.MapToString());
111          File.WriteAllLines("MapToSee.txt", Map.MapToSee());
[16734]112          if (previousExecutionState != ExecutionState.Paused) {
113            InitializeAlgorithm(cancellationToken);
114          }
115          globalScope.Variables.Add(new Variable("TreeModelMap", Map));
[16760]116          EMMAlgorithmRun(cancellationToken);
[16734]117          break;
[16722]118      }
[16734]119
[16722]120    }
[16760]121    private void EMMAlgorithmRun(CancellationToken cancellationToken) {
[16722]122      var bestSelector = new BestSelector();
123      bestSelector.CopySelected = new BoolValue(false);
124      bestSelector.MaximizationParameter.ActualName = "Maximization";
125      bestSelector.NumberOfSelectedSubScopesParameter.ActualName = "Elites";
126      bestSelector.QualityParameter.ActualName = "Quality";
127
128      var populationSize = PopulationSize.Value;
129      var maximumEvaluatedSolutions = MaximumEvaluatedSolutions.Value;
130      var crossover = Crossover;
131      var selector = Selector;
132      var groupSize = GroupSize.Value;
133      var crossoverProbability = CrossoverProbability.Value;
134      var mutator = Mutator;
135      var mutationProbability = MutationProbability.Value;
136      var evaluator = Problem.Evaluator;
137      var analyzer = Analyzer;
138      var rand = RandomParameter.Value;
139      var elites = Elites.Value;
140
141      // cancellation token for the inner operations which should not be immediately cancelled
142      var innerToken = new CancellationToken();
143
[16760]144      while (EvaluatedSolutions < maximumEvaluatedSolutions && !cancellationToken.IsCancellationRequested) {
[16722]145
146        var op4 = executionContext.CreateChildOperation(bestSelector, executionContext.Scope); // select elites
147        ExecuteOperation(executionContext, innerToken, op4);
148
149        var remaining = executionContext.Scope.SubScopes.Single(x => x.Name == "Remaining");
150        executionContext.Scope.SubScopes.AddRange(remaining.SubScopes);
151        var selected = executionContext.Scope.SubScopes.Single(x => x.Name == "Selected");
152        executionContext.Scope.SubScopes.AddRange(selected.SubScopes);
[16760]153        Population.Clear();
154        Population.AddRange(selected.SubScopes.Select(x => new EMMSolution(x)));
[16722]155        executionContext.Scope.SubScopes.Remove(remaining);
156        executionContext.Scope.SubScopes.Remove(selected);
157
[16760]158        var op = executionContext.CreateChildOperation(selector, executionContext.Scope);// select the rest of the Population
[16722]159        ExecuteOperation(executionContext, innerToken, op);
160
161        remaining = executionContext.Scope.SubScopes.Single(x => x.Name == "Remaining");
162        selected = executionContext.Scope.SubScopes.Single(x => x.Name == "Selected");
163
164        for (int i = 0; i < selector.NumberOfSelectedSubScopesParameter.Value.Value; i += 2) {
165          // crossover
166          IScope childScope = null;
167          if (rand.NextDouble() < crossoverProbability) {
168            childScope = new Scope($"{i}+{i + 1}") { Parent = executionContext.Scope };
169            childScope.SubScopes.Add(selected.SubScopes[i]);
170            childScope.SubScopes.Add(selected.SubScopes[i + 1]);
171            var op1 = executionContext.CreateChildOperation(crossover, childScope);
172            ExecuteOperation(executionContext, innerToken, op1);
173            childScope.SubScopes.Clear();
174          }
175
176          childScope = childScope ?? selected.SubScopes[i];
177          // mutation
178          if (rand.NextDouble() < mutationProbability) {
179            var op2 = executionContext.CreateChildOperation(mutator, childScope);
180            ExecuteOperation(executionContext, innerToken, op2);
181          }
182
183          // evaluation
184          if (childScope != null) {
185            var op3 = executionContext.CreateChildOperation(evaluator, childScope);
186            ExecuteOperation(executionContext, innerToken, op3);
187            var qualities = (DoubleValue)childScope.Variables["Quality"].Value;
188            var childSolution = new EMMSolution(childScope);
189            // set child qualities
190            childSolution.Qualities = qualities;
[16760]191            ++EvaluatedSolutions;
192            Population.Add(new EMMSolution(childScope));
[16722]193          } else {// no crossover or mutation were applied, a child was not produced, do nothing
[16760]194            Population.Add(new EMMSolution(selected.SubScopes[i]));
[16722]195          }
196
[16760]197          if (EvaluatedSolutions >= maximumEvaluatedSolutions) {
[16722]198            break;
199          }
200
201        }
[16760]202        globalScope.SubScopes.Replace(Population.Select(x => (IScope)x.Individual));
[16722]203        // run analyzer
204        var analyze = executionContext.CreateChildOperation(analyzer, globalScope);
205        ExecuteOperation(executionContext, innerToken, analyze);
[16760]206        Results.AddOrUpdateResult("Evaluated Solutions", new IntValue(EvaluatedSolutions));
[16722]207      }
208    }
209    protected void InitializeAlgorithm(CancellationToken cancellationToken) {
210      globalScope = new Scope("Global Scope");
211      executionContext = new ExecutionContext(null, this, globalScope);
212
213      // set the execution context for parameters to allow lookup
214      foreach (var parameter in Problem.Parameters.OfType<IValueParameter>()) {  //
215                                                                                 // we need all of these in order for the wiring of the operators to work
216        globalScope.Variables.Add(new Core.Variable(parameter.Name, parameter.Value));
217      }
218      globalScope.Variables.Add(new Core.Variable("Results", Results)); // make results available as a parameter for analyzers etc.
219
220      var rand = RandomParameter.Value;
221      if (SetSeedRandomly) Seed = RandomSeedGenerator.GetSeed();
222      rand.Reset(Seed);
223
224      var populationSize = PopulationSize.Value;
225
226      InitializePopulation(executionContext, cancellationToken, rand);
227
228      // initialize data structures for map clustering
229      var models = new ItemList<ISymbolicExpressionTree>(Map.ModelSet);
230      var map = new ItemList<ItemList<IntValue>>();
231      foreach (var list in Map.Map) {
232        map.Add(new ItemList<IntValue>(list.Select(x => new IntValue(x))));
233      }
234      var clusterNumber = new ItemList<IntValue>(Map.ClusterNumber.Select(x => new IntValue(x)));
235      globalScope.Variables.Add(new Core.Variable("Models", models));
236      globalScope.Variables.Add(new Core.Variable("Map", map));
237      globalScope.Variables.Add(new Core.Variable("ClusterNumber", clusterNumber));
238
[16760]239      EvaluatedSolutions = populationSize;
[16722]240      base.Initialize(cancellationToken);
241    }
242    private void InitializePopulation(ExecutionContext executionContext, CancellationToken cancellationToken, IRandom random) {
243      var creator = Problem.SolutionCreator;
244      var evaluator = Problem.Evaluator;
245      var populationSize = PopulationSize.Value;
[16760]246      Population = new List<IEMMSolution>(populationSize);
[16722]247
248      var parentScope = executionContext.Scope; //main scope for the next step work
249      // first, create all individuals
250      for (int i = 0; i < populationSize; ++i) {
251        var childScope = new Scope(i.ToString()) { Parent = parentScope };
252        ExecuteOperation(executionContext, cancellationToken, executionContext.CreateChildOperation(creator, childScope));
253        var name = ((ISymbolicExpressionTreeCreator)creator).SymbolicExpressionTreeParameter.ActualName;
254        var tree = (ISymbolicExpressionTree)childScope.Variables[name].Value;
255        foreach (var node in tree.IterateNodesPostfix().OfType<TreeModelTreeNode>()) {
256          node.Tree = Map.NewModelForInizializtion(random, out int cluster, out int treeNumber);
[16734]257          node.SetLocalParameters(random, 0.5);
[16722]258          node.ClusterNumer = cluster;
259          node.TreeNumber = treeNumber;
260        }
261        parentScope.SubScopes.Add(childScope);
262      }
263
264      // then, evaluate them and update qualities
265      for (int i = 0; i < populationSize; ++i) {
266        var childScope = parentScope.SubScopes[i];
267        ExecuteOperation(executionContext, cancellationToken, executionContext.CreateChildOperation(evaluator, childScope));
268
269        var qualities = (DoubleValue)childScope.Variables["Quality"].Value;
270        var solution = new EMMSolution(childScope);  // Create solution and push individual inside
271
272        solution.Qualities = qualities;
[16760]273        Population.Add(solution);  // push solution to Population
[16722]274      }
275    }
276  }
277
278}
279
Note: See TracBrowser for help on using the repository browser.