Changeset 7792 for branches/HeuristicLab.EvolutionaryTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding
- Timestamp:
- 05/10/12 17:17:14 (13 years ago)
- Location:
- branches/HeuristicLab.EvolutionaryTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding/3.4
- Files:
-
- 8 edited
Legend:
- Unmodified
- Added
- Removed
-
branches/HeuristicLab.EvolutionaryTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding/3.4/Crossovers/TracingSymbolicExpressionTreeCrossover.cs
r7788 r7792 21 21 22 22 using System; 23 using System.Collections.Generic; 23 24 using System.Linq; 24 25 using HeuristicLab.Common; … … 35 36 /// A base class for operators that perform a crossover of symbolic expression trees. 36 37 /// </summary> 37 [Item("SymbolicExpressionTreeCrossover", 38 "A base class for operators that perform a crossover of symbolic expression trees.")] 38 [Item("SymbolicExpressionTreeCrossover", "A base class for operators that perform a crossover of symbolic expression trees.")] 39 39 [StorableClass] 40 40 public abstract class TracingSymbolicExpressionTreeCrossover : SymbolicExpressionTreeOperator, ISymbolicExpressionTreeCrossover { … … 46 46 47 47 #region Parameter Properties 48 49 48 public ILookupParameter<ItemArray<ISymbolicExpressionTree>> ParentsParameter { 50 49 get { return (ScopeTreeLookupParameter<ISymbolicExpressionTree>)Parameters[ParentsParameterName]; } 51 50 } 52 53 51 public ILookupParameter<ISymbolicExpressionTree> ChildParameter { 54 52 get { return (ILookupParameter<ISymbolicExpressionTree>)Parameters[ChildParameterName]; } 55 53 } 56 57 54 public LookupParameter<CloneMapType> GlobalCloneMapParameter { 58 55 get { return (LookupParameter<CloneMapType>)Parameters[GlobalCloneMapParameterName]; } 59 56 } 60 61 57 public LookupParameter<TraceMapType> GlobalTraceMapParameter { 62 58 get { return (LookupParameter<TraceMapType>)Parameters[GlobalTraceMapParameterName]; } 63 59 } 64 65 60 public LookupParameter<CloneMapType> GlobalFragmentMapParameter { 66 61 get { return (LookupParameter<CloneMapType>)Parameters[GlobalFragmentMapParameterName]; } 67 62 } 68 69 63 #endregion 70 64 71 65 #region Properties 72 73 66 public ItemArray<ISymbolicExpressionTree> Parents { 74 67 get { return ParentsParameter.ActualValue; } 75 68 } 76 77 69 public ISymbolicExpressionTree Child { 78 70 get { return ChildParameter.ActualValue; } 79 71 set { ChildParameter.ActualValue = value; } 80 72 } 81 82 73 public CloneMapType GlobalCloneMap { 83 74 get { return GlobalCloneMapParameter.ActualValue; } 84 75 } 85 76 public TraceMapType GlobalTraceMap { 77 get { return GlobalTraceMapParameter.ActualValue; } 78 } 86 79 public CloneMapType GlobalFragmentMap { 87 80 get { return GlobalFragmentMapParameter.ActualValue; } 88 81 } 89 90 public TraceMapType GlobalTraceMap {91 get { return GlobalTraceMapParameter.ActualValue; }92 }93 94 82 #endregion 95 83 … … 105 93 protected TracingSymbolicExpressionTreeCrossover() 106 94 : base() { 107 Parameters.Add(new ScopeTreeLookupParameter<ISymbolicExpressionTree>(ParentsParameterName, 108 "The parent symbolic expression trees which should be crossed.")); 109 Parameters.Add(new LookupParameter<ISymbolicExpressionTree>(ChildParameterName, 110 "The child symbolic expression tree resulting from the crossover.")); 111 Parameters.Add(new LookupParameter<CloneMapType>(GlobalCloneMapParameterName, 112 "A global map keeping track of trees and their clones (made during selection).")); 113 Parameters.Add(new LookupParameter<CloneMapType>(GlobalFragmentMapParameterName, 114 "A global map keeping track of tree fragments received via crossover.")); 115 Parameters.Add(new LookupParameter<TraceMapType>(GlobalTraceMapParameterName, 116 "A global cache containing tracing info.")); 95 Parameters.Add(new ScopeTreeLookupParameter<ISymbolicExpressionTree>(ParentsParameterName, "The parent symbolic expression trees which should be crossed.")); 96 Parameters.Add(new LookupParameter<ISymbolicExpressionTree>(ChildParameterName, "The child symbolic expression tree resulting from the crossover.")); 97 Parameters.Add(new LookupParameter<CloneMapType>(GlobalCloneMapParameterName, "A global map keeping track of trees and their clones (made during selection).")); 98 Parameters.Add(new LookupParameter<CloneMapType>(GlobalFragmentMapParameterName, "A global map keeping track of tree fragments received via crossover.")); 99 Parameters.Add(new LookupParameter<TraceMapType>(GlobalTraceMapParameterName, "A global cache containing tracing info.")); 117 100 } 118 101 … … 120 103 if (Parents.Length != 2) 121 104 throw new ArgumentException("Number of parents must be exactly two for symbolic expression tree crossover operators."); 105 122 106 // add global trace cache if not already present in global scope 123 107 var gScope = ExecutionContext.Scope; 124 while (gScope.Parent != null) gScope = gScope.Parent; 108 while (gScope.Parent != null) 109 gScope = gScope.Parent; 125 110 if (GlobalTraceMap == null) 126 111 gScope.Variables.Add(new Variable(GlobalTraceMapParameterName, new TraceMapType())); 127 112 if (GlobalFragmentMap == null) 128 113 gScope.Variables.Add(new Variable(GlobalFragmentMapParameterName, new CloneMapType())); 129 // get original parents 114 115 // get original parents (this info will be needed later to construct the genealogy graph) 130 116 var originalParents = new ItemList<IItem>(Parents.Select(x => GlobalCloneMap[x])); 117 131 118 // save the nodes of parent0 in a list so we can track what modifications are made by crossover 132 var nodes0 = Parents[0].IterateNodes().ToList(); 119 var nodes0 = Parents[0].IterateNodesBreadth() as List<ISymbolicExpressionTreeNode>; 120 133 121 //perform crossover 134 122 Child = Crossover(Random, Parents[0], Parents[1]); 123 135 124 // create another list of parent0's nodes, so we can compare it with the first list to see what changed 136 var nodes1 = Child.IterateNodes().ToList(); 125 var nodes1 = Child.IterateNodesBreadth() as List<ISymbolicExpressionTreeNode>; 126 137 127 // compare the two nodes lists and check the difference (comparing node references so we avoid false functional identity). 138 128 // if no difference is found, then it is assumed that the whole tree was swapped with itself (it can happen), so the index is 0 … … 141 131 if (nodes0[i] != nodes1[i]) break; 142 132 if (i == min) i = 0; 143 GlobalTraceMap[Child] = originalParents; 144 GlobalFragmentMap[Child] = new IntValue(i); 133 134 // add heredity information into the global variables 135 GlobalTraceMap[Child] = originalParents; // map child to its corresponding parents from the previous generation 136 GlobalFragmentMap[Child] = new IntValue(i); // map child to the index of its fragment 145 137 return base.Apply(); 146 138 } -
branches/HeuristicLab.EvolutionaryTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding/3.4/Interfaces/ISymbolicExpressionTree.cs
r7439 r7792 31 31 IEnumerable<ISymbolicExpressionTreeNode> IterateNodesPrefix(); 32 32 IEnumerable<ISymbolicExpressionTreeNode> IterateNodesPostfix(); 33 IEnumerable<ISymbolicExpressionTreeNode> IterateNodesBreadth(); 33 34 } 34 35 } -
branches/HeuristicLab.EvolutionaryTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding/3.4/Interfaces/ISymbolicExpressionTreeNode.cs
r7522 r7792 36 36 IEnumerable<ISymbolicExpressionTreeNode> IterateNodesPostfix(); 37 37 IEnumerable<ISymbolicExpressionTreeNode> IterateNodesPrefix(); 38 IEnumerable<ISymbolicExpressionTreeNode> IterateNodesBreadth(); 38 39 void ForEachNodePostfix(Action<ISymbolicExpressionTreeNode> a); 39 40 void ForEachNodePrefix(Action<ISymbolicExpressionTreeNode> a); -
branches/HeuristicLab.EvolutionaryTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding/3.4/Manipulators/TracingSymbolicExpressionTreeManipulator.cs
r7514 r7792 21 21 22 22 using System; 23 using System.Linq; 23 24 using HeuristicLab.Common; 24 25 using HeuristicLab.Core; 26 using HeuristicLab.Data; 25 27 using HeuristicLab.Parameters; 26 28 using HeuristicLab.Persistence.Default.CompositeSerializers.Storable; … … 39 41 private const string GlobalTraceMapParameterName = "GlobalTraceMap"; 40 42 private const string GlobalCloneMapParameterName = "GlobalCloneMap"; 43 private const string GlobalFragmentMapParameterName = "GlobalFragmentMap"; 41 44 42 45 #region Parameter Properties … … 49 52 public LookupParameter<TraceMapType> GlobalTraceMapParameter { 50 53 get { return (LookupParameter<TraceMapType>)Parameters[GlobalTraceMapParameterName]; } 54 } 55 public LookupParameter<CloneMapType> GlobalFragmentMapParameter { 56 get { return (LookupParameter<CloneMapType>)Parameters[GlobalFragmentMapParameterName]; } 51 57 } 52 58 #endregion … … 62 68 get { return GlobalTraceMapParameter.ActualValue; } 63 69 } 70 public CloneMapType GlobalFragmentMap { 71 get { return GlobalFragmentMapParameter.ActualValue; } 72 } 64 73 #endregion 65 74 … … 72 81 Parameters.Add(new LookupParameter<CloneMapType>(GlobalCloneMapParameterName, "A global map keeping track of trees and their clones (made during selection).")); 73 82 Parameters.Add(new LookupParameter<TraceMapType>(GlobalTraceMapParameterName, "A global cache containing tracing info.")); 83 Parameters.Add(new LookupParameter<CloneMapType>(GlobalFragmentMapParameterName, "A global map keeping track of tree fragments received via crossover.")); 74 84 } 75 85 … … 77 87 ISymbolicExpressionTree tree = SymbolicExpressionTreeParameter.ActualValue; 78 88 79 if (GlobalTraceMap == null) { 80 var gScope = ExecutionContext.Scope; 81 while (gScope.Parent != null) gScope = gScope.Parent; 89 var gScope = ExecutionContext.Scope; 90 while (gScope.Parent != null) 91 gScope = gScope.Parent; 92 93 if (GlobalTraceMap == null) 82 94 gScope.Variables.Add(new Variable(GlobalTraceMapParameterName, new TraceMapType())); 83 } 95 if (GlobalFragmentMap == null) 96 gScope.Variables.Add(new Variable(GlobalFragmentMapParameterName, new CloneMapType())); 97 84 98 if (GlobalTraceMap.ContainsKey(tree)) { 85 99 // tree was affected by crossover before mutation 86 // if the tree to be manipulated is already a product of crossover (in the current reproduction phase), then there exists no relationship with the original "parent". 100 // if the tree to be manipulated is already a product of crossover (in the current reproduction phase), 101 // then there exists no relationship with the original "parent". 87 102 // In order to preserve information, a tree clone is created before mutation and added to the trace map. 88 103 var clone = (IItem)tree.Clone(); 89 104 GlobalTraceMap[clone] = GlobalTraceMap[tree]; 90 105 GlobalTraceMap[tree] = new ItemList<IItem> { clone }; 106 GlobalFragmentMap[clone] = GlobalFragmentMap[tree]; 91 107 } else { 92 108 var original = GlobalCloneMap[tree]; 93 109 GlobalTraceMap[tree] = new ItemList<IItem> { original }; 94 110 } 111 var nodes0 = tree.IterateNodesBreadth().ToList(); 95 112 Manipulate(RandomParameter.ActualValue, tree); 113 var nodes1 = tree.IterateNodesBreadth().ToList(); 114 int i, min = Math.Max(nodes0.Count, nodes1.Count); 115 for (i = 0; i != min; ++i) 116 if (nodes0[i] != nodes1[i]) break; 117 if (i == min) i = 0; 118 GlobalFragmentMap[tree] = new IntValue(i); 96 119 97 120 return base.Apply(); -
branches/HeuristicLab.EvolutionaryTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding/3.4/Plugin.cs
r7788 r7792 26 26 27 27 namespace HeuristicLab.Encodings.SymbolicExpressionTreeEncoding { 28 [Plugin("HeuristicLab.Encodings.SymbolicExpressionTreeEncoding","Provides operators and related classes for the symbolic expression tree encoding.", "3.4.2.778 5")]28 [Plugin("HeuristicLab.Encodings.SymbolicExpressionTreeEncoding","Provides operators and related classes for the symbolic expression tree encoding.", "3.4.2.7788")] 29 29 [PluginFile("HeuristicLab.Encodings.SymbolicExpressionTreeEncoding-3.4.dll", PluginFileType.Assembly)] 30 30 [PluginDependency("HeuristicLab.Analysis", "3.3")] -
branches/HeuristicLab.EvolutionaryTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding/3.4/SymbolicExpressionTree.cs
r7439 r7792 85 85 return root.IterateNodesPostfix(); 86 86 } 87 public IEnumerable<ISymbolicExpressionTreeNode> IterateNodesBreadth() { 88 if (root == null) 89 return new SymbolicExpressionTreeNode[0]; 90 return root.IterateNodesBreadth(); 91 } 87 92 88 93 public override IDeepCloneable Clone(Cloner cloner) { -
branches/HeuristicLab.EvolutionaryTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding/3.4/SymbolicExpressionTreeMatching.cs
r7788 r7792 70 70 71 71 public static bool ContainsFragment(this ISymbolicExpressionTree tree, ISymbolicExpressionTreeNode fragment, int mode) { 72 var nodes = tree.IterateNodes Postfix().ToArray();73 var fragments = fragment.IterateNodes Postfix().ToArray();72 var nodes = tree.IterateNodesBreadth() as List<ISymbolicExpressionTreeNode>; 73 var fragments = fragment.IterateNodesBreadth() as List<ISymbolicExpressionTreeNode>; 74 74 return FindMatch(nodes, fragments, mode) != -1; 75 75 } 76 76 77 #region FindMatch signatures78 public static int FindMatch(ISymbolicExpressionTree t0, ISymbolicExpressionTree t1, int mode) {79 return FindMatch(t0.IterateNodesPostfix().ToArray(), t1.IterateNodesPostfix().ToArray(), mode);80 }81 private static int FindMatch(ISymbolicExpressionTreeNode t0, ISymbolicExpressionTreeNode t1, int mode) {82 return FindMatch(t0.IterateNodesPostfix().ToArray(), t1.IterateNodesPostfix().ToArray(), mode);83 }84 private static int FindMatch(ISymbolicExpressionTree t0, ISymbolicExpressionTreeNode t1, int mode) {85 return FindMatch(t0.IterateNodesPostfix().ToArray(), t1.IterateNodesPostfix().ToArray(), mode);86 }87 private static int FindMatch(ISymbolicExpressionTreeNode t0, ISymbolicExpressionTree t1, int mode) {88 return FindMatch(t0.IterateNodesPostfix().ToArray(), t1.IterateNodesPostfix().ToArray(), mode);89 }90 #endregion91 92 77 // convenience methods for less typing :) 93 78 private static IEnumerator<ISymbolicExpressionTreeNode> Enumerator(this ISymbolicExpressionTree tree) { 94 return tree.IterateNodes ().GetEnumerator();79 return tree.IterateNodesBreadth().GetEnumerator(); 95 80 } 96 81 private static IEnumerator<ISymbolicExpressionTreeNode> Enumerator(this ISymbolicExpressionTreeNode tree) { 97 return tree.IterateNodes ().GetEnumerator();82 return tree.IterateNodesBreadth().GetEnumerator(); 98 83 } 99 // method for breath-width iteration of nodes 100 public static IEnumerable<ISymbolicExpressionTreeNode> IterateNodes(this ISymbolicExpressionTree tree) { 101 return IterateNodes(tree.Root); 84 public static int FindMatch(ISymbolicExpressionTree a, ISymbolicExpressionTree b, int mode) { 85 var nodesA = a.IterateNodesBreadth() as List<ISymbolicExpressionTreeNode>; 86 var nodesB = b.IterateNodesBreadth() as List<ISymbolicExpressionTreeNode>; 87 return FindMatch(nodesA, nodesB, mode); 102 88 } 103 104 private static IEnumerable<ISymbolicExpressionTreeNode> IterateNodes(this ISymbolicExpressionTreeNode root) { 105 var list = new List<ISymbolicExpressionTreeNode> { root }; 106 int offset = 0, count = 1; 107 while (offset != count) { 108 var c = count; 109 for (int i = offset; i != count; ++i) { 110 yield return list[i]; // TODO: look into yield performance (vs returning the whole list at the end) 111 if (!list[i].Subtrees.Any()) continue; 112 list.AddRange(list[i].Subtrees); 113 } 114 offset = c; 115 count = list.Count; 116 } 117 //return list; 89 public static int FindMatch(ISymbolicExpressionTreeNode a, ISymbolicExpressionTreeNode b, int mode) { 90 var nodesA = a.IterateNodesBreadth() as List<ISymbolicExpressionTreeNode>; 91 var nodesB = b.IterateNodesBreadth() as List<ISymbolicExpressionTreeNode>; 92 return FindMatch(nodesA, nodesB, mode); 118 93 } 119 120 /// <summary>121 /// This method finds the point where parent and child differ. For instance in the case of crossover,122 /// it will return the node that was swapped into parent0 from parent1123 /// Prerequisites: as the naming implies, heredity should exist between parent and child,124 /// otherwise this method would not make much sense (it would always return the root of child)125 /// </summary>126 /// <param name="parent">The individual from the previous generation that was crossed over or mutated to produce child</param>127 /// <param name="child">The result of a genetic operation applied on parent</param>128 /// <returns>A symbolic expression tree node representing the difference fragment between parent and child</returns>129 public static ISymbolicExpressionTreeNode GetFragmentDiff(ISymbolicExpressionTree parent, ISymbolicExpressionTree child) {130 var nodes1 = parent.IterateNodes().ToList();131 var nodes2 = child.IterateNodes().ToList();132 var e1 = nodes1.AsEnumerable().GetEnumerator();133 var e2 = nodes2.AsEnumerable().GetEnumerator();134 while (e1.MoveNext() && e2.MoveNext()) {135 var comparer = new SymbolicExpressionTreeNodeComparer((int)SimilarityLevel.Exact);136 if (!comparer.Equals(e1.Current, e2.Current)) {137 return e2.Current;138 }139 //if (!e1.Current.IterateNodes().SequenceEqual(e2.Current.IterateNodes(), comparer)) {140 // return e2.Current;141 //} // return the fragment by which child differs from parent142 }143 return null;144 }145 146 94 // returns the index in the sequence 'seq', where pattern 'pat' is matched, or -1 for no match 147 95 // -1 means no match, 0 means perfect match (the sequences overlap, hence the match index is 0) 148 public static int FindMatch( ISymbolicExpressionTreeNode[] seq, ISymbolicExpressionTreeNode[]pat, int mode) {149 int patlen = pat. Length;150 int seqlen = seq. Length;96 public static int FindMatch(List<ISymbolicExpressionTreeNode> seq, List<ISymbolicExpressionTreeNode> pat, int mode) { 97 int patlen = pat.Count; 98 int seqlen = seq.Count; 151 99 if (patlen == 0 || seqlen == 0) return -1; 152 100 var comparer = new SymbolicExpressionTreeNodeComparer(mode); -
branches/HeuristicLab.EvolutionaryTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding/3.4/SymbolicExpressionTreeNode.cs
r7522 r7792 172 172 } 173 173 174 public IEnumerable<ISymbolicExpressionTreeNode> IterateNodesBreadth() { 175 var list = new List<ISymbolicExpressionTreeNode>(GetLength()) { this }; 176 int offset = 0, count = 1; 177 while (offset != count) { 178 var c = count; 179 for (int i = offset; i != count; ++i) 180 if (list[i].SubtreeCount > 0) 181 list.AddRange(list[i].Subtrees); 182 offset = c; 183 count = list.Count; 184 } 185 return list; 186 } 187 174 188 public IEnumerable<ISymbolicExpressionTreeNode> IterateNodesPrefix() { 175 List<ISymbolicExpressionTreeNode> list = new List<ISymbolicExpressionTreeNode>( );189 List<ISymbolicExpressionTreeNode> list = new List<ISymbolicExpressionTreeNode>(GetLength()); 176 190 ForEachNodePrefix((n) => list.Add(n)); 177 191 return list; … … 188 202 189 203 public IEnumerable<ISymbolicExpressionTreeNode> IterateNodesPostfix() { 190 List<ISymbolicExpressionTreeNode> list = new List<ISymbolicExpressionTreeNode>( );204 List<ISymbolicExpressionTreeNode> list = new List<ISymbolicExpressionTreeNode>(GetLength()); 191 205 ForEachNodePostfix((n) => list.Add(n)); 192 206 return list;
Note: See TracChangeset
for help on using the changeset viewer.