Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding.Views/3.4/GraphicalSymbolicExpressionTreeView.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding.Views/3.4/GraphicalSymbolicExpressionTreeView.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding.Views/3.4/GraphicalSymbolicExpressionTreeView.cs	(revision 10347)
@@ -20,4 +20,5 @@
 #endregion
 
+using System.Drawing;
 using System.Windows.Forms;
 using HeuristicLab.Core.Views;
@@ -52,4 +53,12 @@
       symbolicExpressionTreeChart.Enabled = Content != null;
     }
+
+    public void HighlightNode(ISymbolicExpressionTreeNode node, Color color) {
+      symbolicExpressionTreeChart.HighlightNode(node, color);
+    }
+
+    public void HighlightSubtree(ISymbolicExpressionTreeNode subtree, Color color) {
+      symbolicExpressionTreeChart.HighlightSubtree(subtree, color);
+    }
   }
 }
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding.Views/3.4/SymbolicExpressionTreeChart.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding.Views/3.4/SymbolicExpressionTreeChart.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding.Views/3.4/SymbolicExpressionTreeChart.cs	(revision 10347)
@@ -168,4 +168,16 @@
     }
 
+    public void HighlightNode(ISymbolicExpressionTreeNode node, Color color) {
+      var visualNode = GetVisualSymbolicExpressionTreeNode(node);
+      if (visualNode == null) return;
+      visualNode.LineColor = color;
+      RepaintNode(visualNode);
+    }
+
+    public void HighlightSubtree(ISymbolicExpressionTreeNode subtree, Color color) {
+      foreach (var node in subtree.IterateNodesBreadth())
+        HighlightNode(node, color);
+    }
+
     private void GenerateImage() {
       using (Graphics graphics = Graphics.FromImage(image)) {
@@ -267,6 +279,6 @@
     #region methods for painting the symbolic expression tree
 
-    private void DrawFunctionTree(ISymbolicExpressionTree tree, Graphics graphics, int preferredWidth, int preferredHeight, int minHDistance, int minVDistance) {
-      var layoutNodes = layoutAdapter.Convert(tree).ToList();
+    private void DrawFunctionTree(ISymbolicExpressionTree symbolicExpressionTree, Graphics graphics, int preferredWidth, int preferredHeight, int minHDistance, int minVDistance) {
+      var layoutNodes = layoutAdapter.Convert(symbolicExpressionTree).ToList();
       layoutEngine.Reset();
       layoutEngine.Root = layoutNodes[0];
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding/3.4/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding-3.4.csproj
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding/3.4/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding-3.4.csproj	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding/3.4/HeuristicLab.Encodings.SymbolicExpressionTreeEncoding-3.4.csproj	(revision 10347)
@@ -187,5 +187,4 @@
     <Compile Include="Formatters\SymbolicExpressionTreeGraphvizFormatter.cs" />
     <Compile Include="Formatters\SymbolicExpressionTreeLatexFormatter.cs" />
-    <Compile Include="Interfaces\IFragment.cs" />
     <Compile Include="Interfaces\ILayoutAdapter.cs" />
     <Compile Include="Interfaces\ILayoutNode.cs" />
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking.Views/3.4/GenealogyGraphView.Designer.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking.Views/3.4/GenealogyGraphView.Designer.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking.Views/3.4/GenealogyGraphView.Designer.cs	(revision 10347)
@@ -121,9 +121,9 @@
     #endregion
 
-    private System.Windows.Forms.SplitContainer splitContainer;
-    private MainForm.WindowsForms.ViewHost viewHost;
-    private System.Windows.Forms.Panel panel1;
-    private System.Windows.Forms.Panel panel2;
-    private GenealogyGraphChart genealogyGraphChart;
+    protected System.Windows.Forms.SplitContainer splitContainer;
+    protected MainForm.WindowsForms.ViewHost viewHost;
+    protected System.Windows.Forms.Panel panel1;
+    protected System.Windows.Forms.Panel panel2;
+    protected GenealogyGraphChart genealogyGraphChart;
 
   }
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking.Views/3.4/GenealogyGraphView.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking.Views/3.4/GenealogyGraphView.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking.Views/3.4/GenealogyGraphView.cs	(revision 10347)
@@ -7,5 +7,5 @@
   [View("GenealogyGraphView")]
   [Content(typeof(GenealogyGraph), IsDefaultView = false)]
-  public sealed partial class GenealogyGraphView : ItemView {
+  public partial class GenealogyGraphView : ItemView {
     public new IGenealogyGraph Content {
       get { return (IGenealogyGraph)base.Content; }
@@ -31,5 +31,5 @@
     #region Event Handlers (Content)
 
-    public void graphChart_GenealogyGraphNodeClicked(object sender, MouseEventArgs args) {
+    public virtual void graphChart_GenealogyGraphNodeClicked(object sender, MouseEventArgs args) {
       var content = ((VisualGenealogyGraphNode)sender).Data.Content;
       if (content != null) {
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking.Views/3.4/HeuristicLab.EvolutionTracking.Views-3.4.csproj
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking.Views/3.4/HeuristicLab.EvolutionTracking.Views-3.4.csproj	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking.Views/3.4/HeuristicLab.EvolutionTracking.Views-3.4.csproj	(revision 10347)
@@ -161,7 +161,4 @@
   </ItemGroup>
   <ItemGroup>
-    <EmbeddedResource Include="GenealogyGraphView.resx">
-      <DependentUpon>GenealogyGraphView.cs</DependentUpon>
-    </EmbeddedResource>
     <EmbeddedResource Include="Properties\Resources.resx">
       <Generator>ResXFileCodeGenerator</Generator>
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Analyzers/GenealogyAnalyzer.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Analyzers/GenealogyAnalyzer.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Analyzers/GenealogyAnalyzer.cs	(revision 10347)
@@ -15,7 +15,4 @@
   where T : class,IItem {
 
-    private AfterCrossoverOperator<T> afterCrossoverOperator;
-    private AfterManipulatorOperator<T> afterManipulatorOperator;
-    private BeforeManipulatorOperator<T> beforeManipulatorOperator;
     public string CrossoverParentsParameterName { get; set; }
     public string CrossoverChildParameterName { get; set; }
@@ -24,4 +21,9 @@
     public IScopeTreeLookupParameter<DoubleValue> QualityParameter;
     public IScopeTreeLookupParameter<T> PopulationParameter;
+
+    public ICrossoverOperator<T> BeforeCrossoverOperator { get; set; }
+    public ICrossoverOperator<T> AfterCrossoverOperator { get; set; }
+    public IManipulatorOperator<T> BeforeManipulatorOperator { get; set; }
+    public IManipulatorOperator<T> AfterManipulatorOperator { get; set; }
 
     private const string PopulationParameterName = "Population";
@@ -130,4 +132,34 @@
       : base(original, cloner) {
     }
+    [StorableHook(HookType.AfterDeserialization)]
+    private void AfterDeserialization() {
+      // the instrumented operators
+      if (!Parameters.ContainsKey(CrossoverParameterName))
+        Parameters.Add(new LookupParameter<ICrossover>(CrossoverParameterName, "The crossover operator."));
+      if (!Parameters.ContainsKey(ManipulatorParameterName))
+        Parameters.Add(new LookupParameter<IManipulator>(ManipulatorParameterName, "The manipulator operator."));
+      if (!Parameters.ContainsKey(SolutionCreatorParameterName))
+        Parameters.Add(new LookupParameter<ISolutionCreator>(SolutionCreatorParameterName, "The solution creator operator."));
+      // the analyzer parameters
+      if (!Parameters.ContainsKey(EnableCrossoverTrackingParameterName))
+        Parameters.Add(new ValueParameter<BoolValue>(EnableCrossoverTrackingParameterName, new BoolValue(true)));
+      if (!Parameters.ContainsKey(EnableManipulatorTrackingParameterName))
+        Parameters.Add(new ValueParameter<BoolValue>(EnableManipulatorTrackingParameterName, new BoolValue(true)));
+      if (!Parameters.ContainsKey(EnableSolutionCreatorTrackingParameterName))
+        Parameters.Add(new ValueParameter<BoolValue>(EnableSolutionCreatorTrackingParameterName, new BoolValue(true)));
+      // parameters required by the analyzer to do its work
+      if (!Parameters.ContainsKey(GenerationsParameterName))
+        Parameters.Add(new LookupParameter<IntValue>(GenerationsParameterName, "The number of generations so far."));
+      if (!Parameters.ContainsKey(ResultsParameterName))
+        Parameters.Add(new LookupParameter<ResultCollection>(ResultsParameterName));
+      if (!Parameters.ContainsKey(PopulationParameterName)) {
+        PopulationParameter = new ScopeTreeLookupParameter<T>(PopulationParameterName);
+        Parameters.Add(PopulationParameter);
+      }
+      if (!Parameters.ContainsKey(QualityParameterName)) {
+        QualityParameter = new ScopeTreeLookupParameter<DoubleValue>(QualityParameterName);
+        Parameters.Add(QualityParameter);
+      }
+    }
 
     public bool EnabledByDefault {
@@ -146,25 +178,31 @@
         // at the beginning we add the before/after operators to the instrumented operators
         if (EnableCrossoverTracking.Value) {
-          if (afterCrossoverOperator == null) {
-            afterCrossoverOperator = new AfterCrossoverOperator<T>();
-            afterCrossoverOperator.ParentsParameter.ActualName = CrossoverParentsParameterName;
-            afterCrossoverOperator.ChildParameter.ActualName = CrossoverChildParameterName;
-          }
-          var instrumentedCrossover = (InstrumentedOperator)Crossover;
-          instrumentedCrossover.AfterExecutionOperators.Add(afterCrossoverOperator);
+          if (BeforeCrossoverOperator != null) {
+            BeforeCrossoverOperator.ParentsParameter.ActualName = CrossoverParentsParameterName;
+            BeforeCrossoverOperator.ChildParameter.ActualName = CrossoverChildParameterName;
+            var instrumentedCrossover = (InstrumentedOperator)Crossover;
+            instrumentedCrossover.BeforeExecutionOperators.Add(BeforeCrossoverOperator);
+          }
+          if (AfterCrossoverOperator != null) {
+            AfterCrossoverOperator.ParentsParameter.ActualName = CrossoverParentsParameterName;
+            AfterCrossoverOperator.ChildParameter.ActualName = CrossoverChildParameterName;
+            var instrumentedCrossover = (InstrumentedOperator)Crossover;
+            instrumentedCrossover.AfterExecutionOperators.Add(AfterCrossoverOperator);
+          }
         }
 
         if (EnableManipulatorTracking.Value && Manipulator != null) {
-          if (beforeManipulatorOperator == null) {
-            beforeManipulatorOperator = new BeforeManipulatorOperator<T>();
-            beforeManipulatorOperator.ChildParameter.ActualName = ManipulatorChildParameterName;
-          }
-          if (afterManipulatorOperator == null) {
-            afterManipulatorOperator = new AfterManipulatorOperator<T>();
-            afterManipulatorOperator.ChildParameter.ActualName = ManipulatorChildParameterName;
-          }
-          var instrumentedManipulator = (InstrumentedOperator)Manipulator;
-          instrumentedManipulator.BeforeExecutionOperators.Add(beforeManipulatorOperator);
-          instrumentedManipulator.AfterExecutionOperators.Add(afterManipulatorOperator);
+          if (BeforeManipulatorOperator == null) {
+            BeforeManipulatorOperator = new BeforeManipulatorOperator<T>();
+            BeforeManipulatorOperator.ChildParameter.ActualName = ManipulatorChildParameterName;
+            var instrumentedManipulator = (InstrumentedOperator)Manipulator;
+            instrumentedManipulator.BeforeExecutionOperators.Add(BeforeManipulatorOperator);
+          }
+          if (AfterManipulatorOperator == null) {
+            AfterManipulatorOperator = new AfterManipulatorOperator<T>();
+            AfterManipulatorOperator.ChildParameter.ActualName = ManipulatorChildParameterName;
+            var instrumentedManipulator = (InstrumentedOperator)Manipulator;
+            instrumentedManipulator.AfterExecutionOperators.Add(AfterManipulatorOperator);
+          }
         }
       } else {
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Fragment.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Fragment.cs	(revision 10347)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Fragment.cs	(revision 10347)
@@ -0,0 +1,42 @@
+﻿using HeuristicLab.Common;
+using HeuristicLab.Core;
+using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
+
+namespace HeuristicLab.EvolutionTracking {
+  [StorableClass]
+  [Item("Fragment", "An object that stores a ")]
+  public class Fragment : Item, IFragment {
+    [Storable]
+    private int newPos;
+    public int NewPos { get { return newPos; } set { newPos = value; } }
+
+    [Storable]
+    private int oldPos;
+    public int OldPos { get { return oldPos; } set { oldPos = value; } }
+
+    [Storable]
+    private object root;
+    public object Root {
+      get { return root; }
+      set { root = value; }
+    }
+
+    protected Fragment(Fragment original, Cloner cloner)
+      : base(original, cloner) {
+      Root = original.Root;
+      NewPos = original.NewPos;
+      OldPos = original.OldPos;
+    }
+    public override IDeepCloneable Clone(Cloner cloner) {
+      return new Fragment(this, cloner);
+    }
+    public Fragment() { }
+  }
+
+  public class Fragment<T> : Fragment, IFragment<T> where T : class {
+    public new T Root {
+      get { return (T)base.Root; }
+      set { base.Root = value; }
+    }
+  }
+}
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/GenealogyGraph/GenealogyGraph.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/GenealogyGraph/GenealogyGraph.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/GenealogyGraph/GenealogyGraph.cs	(revision 10347)
@@ -76,3 +76,50 @@
   }
 
+  [StorableClass]
+  [Item("GenealogyGraph", "")]
+  public class GenealogyGraph<T> : DirectedGraph, IGenealogyGraph<T> where T : class, IItem {
+    [Storable]
+    private Dictionary<double, LinkedList<IGenealogyGraphNode<T>>> ranks;
+    public Dictionary<double, LinkedList<IGenealogyGraphNode<T>>> Ranks {
+      get { return ranks; }
+      set { ranks = value; }
+    }
+    protected GenealogyGraph(GenealogyGraph<T> original, Cloner cloner)
+      : base(original, cloner) {
+    }
+    public override IDeepCloneable Clone(Cloner cloner) {
+      return new GenealogyGraph<T>(this, cloner);
+    }
+    [StorableConstructor]
+    protected GenealogyGraph(bool deserializing) : base(deserializing) { }
+    public GenealogyGraph() {
+      Ranks = new Dictionary<double, LinkedList<IGenealogyGraphNode<T>>>();
+    }
+    public override void AddVertex(IVertex vertex) {
+      var node = (IGenealogyGraphNode<T>)vertex;
+      if (!Ranks.ContainsKey(node.Rank))
+        Ranks[node.Rank] = new LinkedList<IGenealogyGraphNode<T>>();
+      Ranks[node.Rank].AddLast(node);
+      base.AddVertex(vertex);
+    }
+    public override void RemoveVertex(IVertex vertex) {
+      var node = (IGenealogyGraphNode<T>)vertex;
+      if (Ranks.ContainsKey(node.Rank)) {
+        Ranks[node.Rank].Remove(node);
+      }
+      base.RemoveVertex(vertex);
+    }
+    public event EventHandler GraphUpdated;
+    private void OnGraphUpdated(object sender, EventArgs args) {
+      var updated = GraphUpdated;
+      if (updated != null) updated(sender, args);
+    }
+
+    public new List<IGenealogyGraphNode<T>> this[object content] {
+      get {
+        var result = base[content];
+        return result != null ? result.Cast<IGenealogyGraphNode<T>>().ToList() : null;
+      }
+    }
+  }
 }
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/GenealogyGraph/Interfaces/IGenealogyGraphArc.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/GenealogyGraph/Interfaces/IGenealogyGraphArc.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/GenealogyGraph/Interfaces/IGenealogyGraphArc.cs	(revision 10347)
@@ -26,8 +26,9 @@
     new IGenealogyGraphNode Source { get; set; }
     new IGenealogyGraphNode Target { get; set; }
+    object Data { get; set; }
   }
 
   public interface IGenealogyGraphArc<T> : IGenealogyGraphArc where T : class, IItem {
-    T Data { get; set; }
+    new T Data { get; set; }
   }
 }
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/HeuristicLab.EvolutionTracking-3.4.csproj
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/HeuristicLab.EvolutionTracking-3.4.csproj	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/HeuristicLab.EvolutionTracking-3.4.csproj	(revision 10347)
@@ -106,13 +106,4 @@
       <Private>False</Private>
     </Reference>
-    <Reference Include="HeuristicLab.Problems.DataAnalysis-3.4, Version=3.4.0.0, Culture=neutral, PublicKeyToken=ba48961d6f65dcec, processorArchitecture=MSIL">
-      <Private>False</Private>
-    </Reference>
-    <Reference Include="HeuristicLab.Problems.DataAnalysis.Symbolic.Regression-3.4, Version=3.4.0.0, Culture=neutral, PublicKeyToken=ba48961d6f65dcec, processorArchitecture=MSIL">
-      <Private>False</Private>
-    </Reference>
-    <Reference Include="HeuristicLab.Problems.DataAnalysis.Symbolic.Regression.Views-3.4, Version=3.4.0.0, Culture=neutral, PublicKeyToken=ba48961d6f65dcec, processorArchitecture=MSIL">
-      <Private>False</Private>
-    </Reference>
     <Reference Include="HeuristicLab.Random-3.3, Version=3.3.0.0, Culture=neutral, PublicKeyToken=ba48961d6f65dcec, processorArchitecture=MSIL">
       <SpecificVersion>False</SpecificVersion>
@@ -138,4 +129,7 @@
     <Compile Include="DirectedGraph\Interfaces\IVertex.cs" />
     <Compile Include="DirectedGraph\Vertex.cs" />
+    <Compile Include="Fragment.cs" />
+    <Compile Include="Interfaces\IFragment.cs" />
+    <Compile Include="Operators\BeforeCrossoverOperator.cs" />
     <Compile Include="Operators\AfterCrossoverOperator.cs" />
     <Compile Include="Operators\AfterManipulatorOperator.cs" />
@@ -143,7 +137,4 @@
     <Compile Include="Operators\BeforeManipulatorOperator.cs" />
     <Compile Include="Operators\EvolutionTrackingOperator.cs" />
-    <Compile Include="FPGraph.cs">
-      <SubType>Code</SubType>
-    </Compile>
     <Compile Include="GenealogyGraph\GenealogyGraph.cs" />
     <Compile Include="GenealogyGraph\GenealogyGraphArc.cs" />
@@ -152,17 +143,10 @@
     <Compile Include="GenealogyGraph\Interfaces\IGenealogyGraphArc.cs" />
     <Compile Include="GenealogyGraph\Interfaces\IGenealogyGraphNode.cs" />
+    <Compile Include="Operators\Interfaces\IManipulatorOperator.cs" />
+    <Compile Include="Operators\Interfaces\ICrossoverOperator.cs" />
     <Compile Include="Plugin.cs">
       <SubType>Code</SubType>
     </Compile>
     <Compile Include="Properties\AssemblyInfo.cs" />
-    <Compile Include="SymbolGraph.cs">
-      <SubType>Code</SubType>
-    </Compile>
-  </ItemGroup>
-  <ItemGroup>
-    <ProjectReference Include="..\..\HeuristicLab.Encodings.SymbolicExpressionTreeEncoding\3.4\HeuristicLab.Encodings.SymbolicExpressionTreeEncoding-3.4.csproj">
-      <Project>{06d4a186-9319-48a0-bade-a2058d462eea}</Project>
-      <Name>HeuristicLab.Encodings.SymbolicExpressionTreeEncoding-3.4</Name>
-    </ProjectReference>
   </ItemGroup>
   <ItemGroup>
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Interfaces/IFragment.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Interfaces/IFragment.cs	(revision 10347)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Interfaces/IFragment.cs	(revision 10347)
@@ -0,0 +1,34 @@
+﻿#region License Information
+/* HeuristicLab
+ * Copyright (C) 2002-2013 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
+ *
+ * This file is part of HeuristicLab.
+ *
+ * HeuristicLab is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * HeuristicLab is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
+ */
+#endregion
+using HeuristicLab.Core;
+
+namespace HeuristicLab.EvolutionTracking {
+
+  public interface IFragment : IItem {
+    object Root { get; set; }
+    int NewPos { get; set; }
+    int OldPos { get; set; }
+  }
+
+  public interface IFragment<T> : IFragment where T : class {
+    new T Root { get; set; }
+  }
+}
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/AfterCrossoverOperator.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/AfterCrossoverOperator.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/AfterCrossoverOperator.cs	(revision 10347)
@@ -20,5 +20,4 @@
 #endregion
 
-using System.Linq;
 using HeuristicLab.Common;
 using HeuristicLab.Core;
@@ -29,10 +28,9 @@
   [StorableClass]
   [Item("AfterCrossoverOperator", "A generic operator that can record genealogical relationships between crossover parents and children.")]
-  public class AfterCrossoverOperator<T> : EvolutionTrackingOperator
-    where T : class,IItem {
+  public class AfterCrossoverOperator<T> : EvolutionTrackingOperator, ICrossoverOperator<T> where T : class,IItem {
     private const string defaultParentsParameterName = "Parents";
     private const string defaultChildParameterName = "Child";
-    public IScopeTreeLookupParameter<T> ParentsParameter;
-    public ILookupParameter<T> ChildParameter;
+    public IScopeTreeLookupParameter<T> ParentsParameter { get; set; }
+    public ILookupParameter<T> ChildParameter { get; set; }
 
     protected AfterCrossoverOperator(AfterCrossoverOperator<T> original, Cloner cloner)
@@ -51,19 +49,4 @@
 
     public override IOperation Apply() {
-      //      var parentVertices = ParentsParameter.ActualValue.Select(x => GenealogyGraph[x].Last()).ToList();
-      var lastGen = GenealogyGraph.Ranks[Generations.Value].ToList();
-      var parentVertices = ExecutionContext.Scope.SubScopes.Select(s => lastGen[int.Parse(s.Name)]).ToList(); // because the individuals in the execution scope are copies of the ones in the graph
-
-      var childVertex = new GenealogyGraphNode<T> {
-        Content = ChildParameter.ActualValue,
-        Rank = parentVertices[0].Rank + 1
-      };
-      GenealogyGraph.AddVertex(childVertex);
-      foreach (var v in parentVertices) {
-        childVertex.AddReverseArc(v);
-        v.AddForwardArc(childVertex);
-      }
-      //      if (parentVertices[0].Content == parentVertices[1].Content)
-      //        throw new Exception("Self-crossover");
       return base.Apply();
     }
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/AfterManipulatorOperator.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/AfterManipulatorOperator.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/AfterManipulatorOperator.cs	(revision 10347)
@@ -28,9 +28,8 @@
   [StorableClass]
   [Item("AfterCrossoverOperator", "Performs an action after the crossover operator is applied.")]
-  public class AfterManipulatorOperator<T> : EvolutionTrackingOperator
-    where T : class,IItem {
+  public class AfterManipulatorOperator<T> : EvolutionTrackingOperator, IManipulatorOperator<T> where T : class,IItem {
 
     private const string ChildParameterName = "Child";
-    public ILookupParameter<T> ChildParameter;
+    public ILookupParameter<T> ChildParameter { get; set; }
 
     protected AfterManipulatorOperator(AfterManipulatorOperator<T> original, Cloner cloner)
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/AfterSolutionCreatorOperator.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/AfterSolutionCreatorOperator.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/AfterSolutionCreatorOperator.cs	(revision 10347)
@@ -21,4 +21,5 @@
 
 using HeuristicLab.Core;
+using HeuristicLab.Parameters;
 using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
 
@@ -29,4 +30,11 @@
     where T : class,IItem {
 
+    private const string CurrentScopeParameterName = "CurrentScope";
+
+    public ScopeParameter CurrentScopeParameter {
+      get { return (ScopeParameter)Parameters[CurrentScopeParameterName]; }
+    }
+    public IScope CurrentScope { get { return CurrentScopeParameter.ActualValue; } }
+
     public override IOperation Apply() {
       return base.Apply();
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/BeforeCrossoverOperator.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/BeforeCrossoverOperator.cs	(revision 10347)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/BeforeCrossoverOperator.cs	(revision 10347)
@@ -0,0 +1,83 @@
+﻿#region License Information
+/* HeuristicLab
+ * Copyright (C) 2002-2014 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
+ *
+ * This file is part of HeuristicLab.
+ *
+ * HeuristicLab is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * HeuristicLab is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
+ */
+#endregion
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using HeuristicLab.Common;
+using HeuristicLab.Core;
+using HeuristicLab.Parameters;
+using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
+
+namespace HeuristicLab.EvolutionTracking {
+  [StorableClass]
+  [Item("AfterCrossoverOperator", "A generic operator that can record genealogical relationships between crossover parents and children.")]
+  public class BeforeCrossoverOperator<T> : EvolutionTrackingOperator, ICrossoverOperator<T> where T : class,IItem {
+    private const string defaultParentsParameterName = "Parents";
+    private const string defaultChildParameterName = "Child";
+
+    public IScopeTreeLookupParameter<T> ParentsParameter { get; set; }
+    public ILookupParameter<T> ChildParameter { get; set; }
+
+    protected BeforeCrossoverOperator(BeforeCrossoverOperator<T> original, Cloner cloner)
+      : base(original, cloner) {
+    }
+    public override IDeepCloneable Clone(Cloner cloner) {
+      return new BeforeCrossoverOperator<T>(this, cloner);
+    }
+
+    public BeforeCrossoverOperator() {
+      ParentsParameter = new ScopeTreeLookupParameter<T>(defaultParentsParameterName);
+      ChildParameter = new LookupParameter<T>(defaultChildParameterName);
+      Parameters.Add(ParentsParameter);
+      Parameters.Add(ChildParameter);
+    }
+
+    protected List<IGenealogyGraphNode<T>> CurrentGeneration {
+      get {
+        if (GenealogyGraph.Ranks.ContainsKey(Generations.Value))
+          return GenealogyGraph.Ranks[Generations.Value].Cast<IGenealogyGraphNode<T>>().ToList();
+        return null;
+      }
+    }
+
+    public override IOperation Apply() {
+      if (CurrentGeneration == null) throw new Exception();
+      // we get the parents by parsing the scope name because the individuals in the execution scope are clones of the ones saved in the graph
+      var parentVertices = ExecutionContext.Scope.SubScopes.Select(s => CurrentGeneration[int.Parse(s.Name)]).ToList();
+
+      var parents = ParentsParameter.ActualValue.ToList();
+
+      var childVertex = new GenealogyGraphNode<T> {
+        // the child parameter does not have a value yet (it will be assigned after crossover), but the first parent is actually the future child so we use this
+        Content = parents[0],
+        Rank = parentVertices[0].Rank + 1
+      };
+      GenealogyGraph.AddVertex(childVertex);
+      foreach (var v in parentVertices) {
+        childVertex.AddReverseArc(v);
+        v.AddForwardArc(childVertex);
+      }
+
+      return base.Apply();
+    }
+  }
+}
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/BeforeManipulatorOperator.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/BeforeManipulatorOperator.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/BeforeManipulatorOperator.cs	(revision 10347)
@@ -29,9 +29,8 @@
   [StorableClass]
   [Item("AfterCrossoverOperator", "Performs an action after the crossover operator is applied.")]
-  public class BeforeManipulatorOperator<T> : EvolutionTrackingOperator
-    where T : class,IItem {
+  public class BeforeManipulatorOperator<T> : EvolutionTrackingOperator, IManipulatorOperator<T> where T : class,IItem {
 
     private const string ChildParameterName = "Child";
-    public ILookupParameter<T> ChildParameter;
+    public ILookupParameter<T> ChildParameter { get; set; }
 
     protected BeforeManipulatorOperator(BeforeManipulatorOperator<T> original, Cloner cloner)
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/Interfaces/ICrossoverOperator.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/Interfaces/ICrossoverOperator.cs	(revision 10347)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/Interfaces/ICrossoverOperator.cs	(revision 10347)
@@ -0,0 +1,8 @@
+﻿using HeuristicLab.Core;
+
+namespace HeuristicLab.EvolutionTracking {
+  public interface ICrossoverOperator<T> : IOperator where T : class,IItem {
+    IScopeTreeLookupParameter<T> ParentsParameter { get; set; }
+    ILookupParameter<T> ChildParameter { get; set; }
+  }
+}
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/Interfaces/IManipulatorOperator.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/Interfaces/IManipulatorOperator.cs	(revision 10347)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.EvolutionTracking/3.4/Operators/Interfaces/IManipulatorOperator.cs	(revision 10347)
@@ -0,0 +1,7 @@
+﻿using HeuristicLab.Core;
+
+namespace HeuristicLab.EvolutionTracking {
+  public interface IManipulatorOperator<T> : IOperator where T : class,IItem {
+    ILookupParameter<T> ChildParameter { get; set; }
+  }
+}
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic.Views/3.4/HeuristicLab.Problems.DataAnalysis.Symbolic.Views-3.4.csproj
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic.Views/3.4/HeuristicLab.Problems.DataAnalysis.Symbolic.Views-3.4.csproj	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic.Views/3.4/HeuristicLab.Problems.DataAnalysis.Symbolic.Views-3.4.csproj	(revision 10347)
@@ -219,4 +219,7 @@
       <DependentUpon>SlidingWindowDataView.cs</DependentUpon>
     </Compile>
+    <Compile Include="SymbolicDataAnalysisGenealogyGraphView.cs">
+      <SubType>UserControl</SubType>
+    </Compile>
     <Compile Include="TextualSymbolicDataAnalysisModelView.cs">
       <SubType>UserControl</SubType>
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic.Views/3.4/SymbolicDataAnalysisGenealogyGraphView.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic.Views/3.4/SymbolicDataAnalysisGenealogyGraphView.cs	(revision 10347)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic.Views/3.4/SymbolicDataAnalysisGenealogyGraphView.cs	(revision 10347)
@@ -0,0 +1,24 @@
+﻿using System.Drawing;
+using System.Linq;
+using System.Windows.Forms;
+using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
+using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding.Views;
+using HeuristicLab.EvolutionTracking;
+using HeuristicLab.EvolutionTracking.Views;
+using HeuristicLab.MainForm;
+using HeuristicLab.MainForm.WindowsForms;
+
+namespace HeuristicLab.Problems.DataAnalysis.Symbolic.Views {
+  [View("GenealogyGraphView")]
+  [Content(typeof(GenealogyGraph), IsDefaultView = false)]
+  public class SymbolicDataAnalysisGenealogyGraphView : GenealogyGraphView {
+    public override void graphChart_GenealogyGraphNodeClicked(object sender, MouseEventArgs args) {
+      base.graphChart_GenealogyGraphNodeClicked(sender, args);
+      var visualNode = (VisualGenealogyGraphNode)sender;
+      var graphNode = (IGenealogyGraphNode<ISymbolicExpressionTree>)visualNode.Data;
+      var fragment = (IFragment<ISymbolicExpressionTreeNode>)graphNode.InArcs.Last().Data;
+      var treeView = (GraphicalSymbolicExpressionTreeView)viewHost.ActiveView;
+      treeView.HighlightSubtree(fragment.Root, Color.RoyalBlue);
+    }
+  }
+}
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Analyzers/SymbolicDataAnalysisPopulationDiversityAnalyzer.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Analyzers/SymbolicDataAnalysisPopulationDiversityAnalyzer.cs	(revision 10347)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Analyzers/SymbolicDataAnalysisPopulationDiversityAnalyzer.cs	(revision 10347)
@@ -0,0 +1,201 @@
+﻿#region License Information
+/* HeuristicLab
+ * Copyright (C) 2002-2014 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
+ *
+ * This file is part of HeuristicLab.
+ *
+ * HeuristicLab is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * HeuristicLab is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
+ */
+#endregion
+
+using System.Linq;
+using HeuristicLab.Analysis;
+using HeuristicLab.Common;
+using HeuristicLab.Core;
+using HeuristicLab.Data;
+using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
+using HeuristicLab.Operators;
+using HeuristicLab.Optimization;
+using HeuristicLab.Parameters;
+using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
+
+// type definitions for ease of use
+
+namespace HeuristicLab.Problems.DataAnalysis.Symbolic {
+  /// <summary>
+  /// Population diversity analyzer
+  /// </summary>
+  [Item("SymbolicDataAnalysisPopulationDiversityAnalyzer", "An operator that tracks population diversity")]
+  [StorableClass]
+  public sealed class SymbolicDataAnalysisPopulationDiversityAnalyzer : SingleSuccessorOperator, IAnalyzer {
+    #region Parameter names
+    private const string MaximumSymbolicExpressionTreeDepthParameterName = "MaximumSymbolicExpressionTreeDepth";
+    private const string SymbolicExpressionTreeParameterName = "SymbolicExpressionTree";
+    private const string UpdateIntervalParameterName = "UpdateInterval";
+    private const string UpdateCounterParameterName = "UpdateCounter";
+    private const string ResultsParameterName = "Results";
+    private const string GenerationsParameterName = "Generations";
+    private const string StoreHistoryParameterName = "StoreHistory";
+    // comparer parameters
+    private const string MatchVariablesParameterName = "MatchVariableNames";
+    private const string MatchVariableWeightsParameterName = "MatchVariableWeights";
+    private const string MatchConstantValuesParameterName = "MatchConstantValues";
+    private const string SimilarityValuesParmeterName = "Similarity";
+
+    #endregion
+
+    #region Parameters
+    public IValueLookupParameter<IntValue> MaximumSymbolicExpressionTreeDepthParameter {
+      get { return (IValueLookupParameter<IntValue>)Parameters[MaximumSymbolicExpressionTreeDepthParameterName]; }
+    }
+    public ValueParameter<IntValue> UpdateIntervalParameter {
+      get { return (ValueParameter<IntValue>)Parameters[UpdateIntervalParameterName]; }
+    }
+    public ValueParameter<IntValue> UpdateCounterParameter {
+      get { return (ValueParameter<IntValue>)Parameters[UpdateCounterParameterName]; }
+    }
+    public LookupParameter<ResultCollection> ResultsParameter {
+      get { return (LookupParameter<ResultCollection>)Parameters[ResultsParameterName]; }
+    }
+    public LookupParameter<IntValue> GenerationsParameter {
+      get { return (LookupParameter<IntValue>)Parameters[GenerationsParameterName]; }
+    }
+    public ValueParameter<BoolValue> StoreHistoryParameter {
+      get { return (ValueParameter<BoolValue>)Parameters[StoreHistoryParameterName]; }
+    }
+    public IScopeTreeLookupParameter<ISymbolicExpressionTree> SymbolicExpressionTreeParameter {
+      get { return (IScopeTreeLookupParameter<ISymbolicExpressionTree>)Parameters[SymbolicExpressionTreeParameterName]; }
+    }
+    public ValueParameter<BoolValue> MatchVariableNamesParameter {
+      get { return (ValueParameter<BoolValue>)Parameters[MatchVariablesParameterName]; }
+    }
+    public ValueParameter<BoolValue> MatchVariableWeightsParameter {
+      get { return (ValueParameter<BoolValue>)Parameters[MatchVariableWeightsParameterName]; }
+    }
+    public ValueParameter<BoolValue> MatchConstantValuesParameter {
+      get { return (ValueParameter<BoolValue>)Parameters[MatchConstantValuesParameterName]; }
+    }
+    public ILookupParameter<DoubleValue> SimilarityParameter {
+      get { return (ILookupParameter<DoubleValue>)Parameters[SimilarityValuesParmeterName]; }
+    }
+    #endregion
+
+    #region Parameter properties
+    public IntValue MaximumSymbolicExpressionTreeDepth { get { return MaximumSymbolicExpressionTreeDepthParameter.ActualValue; } }
+    public IntValue UpdateInterval { get { return UpdateIntervalParameter.Value; } }
+    public IntValue UpdateCounter { get { return UpdateCounterParameter.Value; } }
+    public ResultCollection Results { get { return ResultsParameter.ActualValue; } }
+    public IntValue Generations { get { return GenerationsParameter.ActualValue; } }
+    public BoolValue StoreHistory { get { return StoreHistoryParameter.Value; } }
+    #endregion
+
+    [StorableConstructor]
+    private SymbolicDataAnalysisPopulationDiversityAnalyzer(bool deserializing)
+      : base(deserializing) {
+    }
+
+    private SymbolicDataAnalysisPopulationDiversityAnalyzer(
+      SymbolicDataAnalysisPopulationDiversityAnalyzer original, Cloner cloner)
+      : base(original, cloner) {
+    }
+
+    public override IDeepCloneable Clone(Cloner cloner) {
+      return new SymbolicDataAnalysisPopulationDiversityAnalyzer(this, cloner);
+    }
+
+    public SymbolicDataAnalysisPopulationDiversityAnalyzer() {
+      // add parameters
+      Parameters.Add(new ScopeTreeLookupParameter<ISymbolicExpressionTree>(SymbolicExpressionTreeParameterName, "The symbolic expression trees to analyze."));
+      Parameters.Add(new ValueParameter<IntValue>(UpdateIntervalParameterName, "The interval in which the tree length analysis should be applied.", new IntValue(1)));
+      Parameters.Add(new ValueParameter<IntValue>(UpdateCounterParameterName, "The value which counts how many times the operator was called since the last update", new IntValue(0)));
+      Parameters.Add(new ValueLookupParameter<ResultCollection>(ResultsParameterName, "The results collection where the analysis values should be stored."));
+      Parameters.Add(new LookupParameter<IntValue>(GenerationsParameterName, "The number of generations so far."));
+      Parameters.Add(new ValueParameter<BoolValue>(MatchVariablesParameterName, "Specify if the symbolic expression tree comparer should match variable names.", new BoolValue(true)));
+      Parameters.Add(new ValueParameter<BoolValue>(MatchVariableWeightsParameterName, "Specify if the symbolic expression tree comparer should match variable weights.", new BoolValue(true)));
+      Parameters.Add(new ValueParameter<BoolValue>(MatchConstantValuesParameterName, "Specify if the symbolic expression tree comparer should match constant values.", new BoolValue(true)));
+      Parameters.Add(new ValueParameter<BoolValue>(StoreHistoryParameterName, "True if the tree lengths history of the population should be stored.", new BoolValue(false)));
+      Parameters.Add(new LookupParameter<DoubleValue>(SimilarityValuesParmeterName, ""));
+      Parameters.Add(new ValueLookupParameter<IntValue>(MaximumSymbolicExpressionTreeDepthParameterName, "The maximal depth of the symbolic expression tree (a tree with one node has depth = 0)."));
+      UpdateCounterParameter.Hidden = true;
+      UpdateIntervalParameter.Hidden = true;
+    }
+
+    [StorableHook(HookType.AfterDeserialization)]
+    private void AfterDeserialization() {
+      if (!Parameters.ContainsKey(MaximumSymbolicExpressionTreeDepthParameterName)) {
+        Parameters.Add(new ValueLookupParameter<IntValue>(MaximumSymbolicExpressionTreeDepthParameterName, "The maximal depth of the symbolic expression tree (a tree with one node has depth = 0)."));
+      }
+    }
+
+    #region IStatefulItem members
+    public override void InitializeState() {
+      UpdateCounter.Value = 0;
+      base.InitializeState();
+    }
+    #endregion
+
+    public bool EnabledByDefault {
+      get { return true; }
+    }
+
+    public override IOperation Apply() {
+      if (SimilarityParameter.ActualValue == null || SimilarityParameter.ActualValue.Value.IsAlmost(-1.0)) {
+        UpdateCounter.Value++;
+        if (UpdateCounter.Value != UpdateInterval.Value) return base.Apply();
+        UpdateCounter.Value = 0;
+        var trees = SymbolicExpressionTreeParameter.ActualValue.ToList();
+
+        SimilarityParameter.ActualValue = new DoubleValue();
+
+        var comp = new SymbolicExpressionTreeNodeSimilarityComparer {
+          MatchConstantValues = MatchConstantValuesParameter.Value.Value,
+          MatchVariableNames = MatchVariableNamesParameter.Value.Value,
+          MatchVariableWeights = MatchVariableWeightsParameter.Value.Value
+        };
+
+        var operations = new OperationCollection { Parallel = true };
+        foreach (var tree in trees) {
+          var op = new SymbolicDataAnalysisExpressionTreeSimilarityCalculator {
+            CurrentSymbolicExpressionTree = tree,
+            SimilarityComparer = comp,
+            MaximumTreeDepth = MaximumSymbolicExpressionTreeDepth.Value
+          };
+          var operation = ExecutionContext.CreateChildOperation(op, ExecutionContext.Scope);
+          operations.Add(operation);
+        }
+        return new OperationCollection { operations, ExecutionContext.CreateOperation(this) };
+      }
+
+      var results = ResultsParameter.ActualValue;
+      // population diversity
+      DataTable populationDiversityTable;
+      if (!results.ContainsKey("PopulationDiversity")) {
+        populationDiversityTable = new DataTable("PopulationDiversity") { VisualProperties = { YAxisTitle = "Diversity" } };
+        results.Add(new Result("PopulationDiversity", populationDiversityTable));
+      }
+      populationDiversityTable = (DataTable)results["PopulationDiversity"].Value;
+      if (!populationDiversityTable.Rows.ContainsKey("Diversity"))
+        populationDiversityTable.Rows.Add(new DataRow("Diversity") { VisualProperties = { StartIndexZero = true } });
+
+      int length = SymbolicExpressionTreeParameter.ActualValue.Length;
+      var similarity = SimilarityParameter.ActualValue.Value / (length * (length - 1) / 2.0);
+      var diversity = 1 - similarity;
+      SimilarityParameter.ActualValue.Value = -1.0;
+
+      populationDiversityTable.Rows["Diversity"].Values.Add(diversity);
+
+      return base.Apply();
+    }
+  }
+}
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Crossovers/MultiSymbolicDataAnalysisExpressionCrossover.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Crossovers/MultiSymbolicDataAnalysisExpressionCrossover.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Crossovers/MultiSymbolicDataAnalysisExpressionCrossover.cs	(revision 10347)
@@ -109,4 +109,6 @@
       InitializeOperators();
       name = "MultiSymbolicDataAnalysisExpressionCrossover";
+
+      SelectedOperatorParameter.ActualName = "SelectedCrossoverOperator";
     }
 
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/HeuristicLab.Problems.DataAnalysis.Symbolic-3.4.csproj
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/HeuristicLab.Problems.DataAnalysis.Symbolic-3.4.csproj	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/HeuristicLab.Problems.DataAnalysis.Symbolic-3.4.csproj	(revision 10347)
@@ -174,4 +174,5 @@
   <ItemGroup>
     <Compile Include="Analyzers\SymbolicDataAnalysisGenealogyAnalyzer.cs" />
+    <Compile Include="Analyzers\SymbolicDataAnalysisPopulationDiversityAnalyzer.cs" />
     <Compile Include="Analyzers\SymbolicDataAnalysisSingleObjectiveValidationParetoBestSolutionAnalyzer.cs" />
     <Compile Include="Analyzers\SymbolicDataAnalysisSingleObjectiveTrainingParetoBestSolutionAnalyzer.cs" />
@@ -193,4 +194,6 @@
     <Compile Include="SlidingWindow\SlidingWindowQualitiesAnalyzer.cs" />
     <Compile Include="SlidingWindow\SlidingWindowVisualizer.cs" />
+    <Compile Include="SymbolGraph\FPGraph.cs" />
+    <Compile Include="SymbolGraph\SymbolGraph.cs" />
     <Compile Include="SymbolicDataAnalysisExpressionTreeMatching.cs" />
     <Compile Include="SymbolicDataAnalysisExpressionTreeSimilarityCalculator.cs" />
@@ -290,4 +293,8 @@
     <Compile Include="Symbols\VariableConditionTreeNode.cs" />
     <Compile Include="Symbols\VariableTreeNode.cs" />
+    <Compile Include="Tracking\SymbolicDataAnalysExpressionAfterCrossoverOperator.cs" />
+    <Compile Include="Tracking\SymbolicDataAnalysExpressionBeforeCrossoverOperator.cs" />
+    <Compile Include="Tracking\SymbolicDataAnalysisExpressionAfterManipulatorOperator.cs" />
+    <Compile Include="Tracking\SymbolicDataAnalysisExpressionBeforeManipulatorOperator.cs" />
     <None Include="HeuristicLab.snk" />
     <None Include="Plugin.cs.frame" />
@@ -335,7 +342,5 @@
     </ProjectReference>
   </ItemGroup>
-  <ItemGroup>
-    <Folder Include="Tracking\" />
-  </ItemGroup>
+  <ItemGroup />
   <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
   <!-- To modify your build process, add your task inside one of the targets below and uncomment it. 
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SlidingWindow/SlidingWindowQualitiesAnalyzer.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SlidingWindow/SlidingWindowQualitiesAnalyzer.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SlidingWindow/SlidingWindowQualitiesAnalyzer.cs	(revision 10347)
@@ -20,14 +20,9 @@
 #endregion
 
-using System;
-using System.Collections.Generic;
 using System.Linq;
-using System.Text;
-using System.Threading;
 using HeuristicLab.Analysis;
 using HeuristicLab.Common;
 using HeuristicLab.Core;
 using HeuristicLab.Data;
-using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
 using HeuristicLab.Optimization;
 using HeuristicLab.Parameters;
@@ -58,7 +53,6 @@
     }
 
-    public ILookupParameter<ISymbolicDataAnalysisExpressionTreeInterpreter> SymbolicExpressionTreeInterpreter
-    {
-      get  {return(ILookupParameter<ISymbolicDataAnalysisExpressionTreeInterpreter>)Parameters[SymbolicExpressionTreeInterpreterParameterName]; }
+    public ILookupParameter<ISymbolicDataAnalysisExpressionTreeInterpreter> SymbolicExpressionTreeInterpreter {
+      get { return (ILookupParameter<ISymbolicDataAnalysisExpressionTreeInterpreter>)Parameters[SymbolicExpressionTreeInterpreterParameterName]; }
     }
 
@@ -70,10 +64,10 @@
     }
 
-    
+
 
     [StorableConstructor]
     private SlidingWindowQualitiesAnalyzer(bool deserializing) : base(deserializing) { }
 
-    public SlidingWindowQualitiesAnalyzer() { 
+    public SlidingWindowQualitiesAnalyzer() {
       Parameters.Add(new ValueLookupParameter<IDataAnalysisProblemData>(ProblemDataParameterName, "The problem data on which the symbolic data analysis solution should be evaluated."));
       Parameters.Add(new LookupParameter<IEvaluator>(EvaluatorParameterName, ""));
@@ -81,5 +75,6 @@
       Parameters.Add(new LookupParameter<ISymbolicDataAnalysisExpressionTreeInterpreter>(SymbolicExpressionTreeInterpreterParameterName, ""));
 
-      ProblemDataParameter.Hidden = true;}
+      ProblemDataParameter.Hidden = true;
+    }
 
     [StorableHook(HookType.AfterDeserialization)]
@@ -87,6 +82,5 @@
     }
 
-    public override IOperation Apply()
-    {
+    public override IOperation Apply() {
       if (FitnessCalculationPartitionParameter.ActualValue == null)
         // do nothing because the sliding window hasn't been initialized yet
@@ -97,11 +91,11 @@
       if (!results.ContainsKey("Best training solution")) return base.Apply();
 
-      var problemData = (IRegressionProblemData) ProblemDataParameter.ActualValue;
+      var problemData = (IRegressionProblemData)ProblemDataParameter.ActualValue;
       var evaluator =
-        (SymbolicDataAnalysisSingleObjectiveEvaluator<IRegressionProblemData>) EvaluatorParameter.ActualValue;
+        (SymbolicDataAnalysisSingleObjectiveEvaluator<IRegressionProblemData>)EvaluatorParameter.ActualValue;
       var context = new Core.ExecutionContext(ExecutionContext, evaluator, new Scope());
       var fitnessCalculationPartition = FitnessCalculationPartitionParameter.ActualValue;
 
-      var bestSolution = (ISymbolicDataAnalysisSolution) results["Best training solution"].Value;
+      var bestSolution = (ISymbolicDataAnalysisSolution)results["Best training solution"].Value;
       var bestModel = bestSolution.Model;
       var bestTree = bestModel.SymbolicExpressionTree;
@@ -110,12 +104,11 @@
         results.Add(new Result(SlidingWindowQualitiesResultName, new DataTable(SlidingWindowQualitiesResultName)));
       }
-      var swQualitiesTable = (DataTable) results[SlidingWindowQualitiesResultName].Value;
+      var swQualitiesTable = (DataTable)results[SlidingWindowQualitiesResultName].Value;
 
       // compute before quality
       var beforeQuality = 0.0;
       if (!swQualitiesTable.Rows.ContainsKey("Before Quality"))
-        swQualitiesTable.Rows.Add(new DataRow("Before Quality") {VisualProperties = {StartIndexZero = true}});
-      if (fitnessCalculationPartition.Start > problemData.TrainingPartition.Start)
-      {
+        swQualitiesTable.Rows.Add(new DataRow("Before Quality") { VisualProperties = { StartIndexZero = true } });
+      if (fitnessCalculationPartition.Start > problemData.TrainingPartition.Start) {
         var beforeRange = new IntRange(problemData.TrainingPartition.Start, fitnessCalculationPartition.Start);
         beforeQuality = evaluator.Evaluate(context, bestTree, problemData, Enumerable.Range(beforeRange.Start, beforeRange.Size));
@@ -124,23 +117,22 @@
 
       // compute current quality
-      var currentQuality = ((DoubleValue) results["CurrentBestQuality"].Value).Value;
+      var currentQuality = ((DoubleValue)results["CurrentBestQuality"].Value).Value;
       if (!swQualitiesTable.Rows.ContainsKey("Current Quality"))
-        swQualitiesTable.Rows.Add(new DataRow("Current Quality") {VisualProperties = {StartIndexZero = true}});
+        swQualitiesTable.Rows.Add(new DataRow("Current Quality") { VisualProperties = { StartIndexZero = true } });
       swQualitiesTable.Rows["Current Quality"].Values.Add(currentQuality);
 
       // compute after quality
-      if (fitnessCalculationPartition.End < problemData.TrainingPartition.End)
-      {
+      if (fitnessCalculationPartition.End < problemData.TrainingPartition.End) {
         var afterRange = new IntRange(fitnessCalculationPartition.End, problemData.TrainingPartition.End);
         var afterQuality = evaluator.Evaluate(context, bestTree, problemData,
           Enumerable.Range(afterRange.Start, afterRange.Size));
         if (!swQualitiesTable.Rows.ContainsKey("After Quality"))
-          swQualitiesTable.Rows.Add(new DataRow("After Quality") {VisualProperties = {StartIndexZero = true}});
+          swQualitiesTable.Rows.Add(new DataRow("After Quality") { VisualProperties = { StartIndexZero = true } });
         swQualitiesTable.Rows["After Quality"].Values.Add(afterQuality);
       }
       // compute test quality
       if (!swQualitiesTable.Rows.ContainsKey("Test Quality"))
-        swQualitiesTable.Rows.Add(new DataRow("Test Quality") {VisualProperties = {StartIndexZero = true}});
-      var regressionSolution = (IRegressionSolution) bestSolution;
+        swQualitiesTable.Rows.Add(new DataRow("Test Quality") { VisualProperties = { StartIndexZero = true } });
+      var regressionSolution = (IRegressionSolution)bestSolution;
       swQualitiesTable.Rows["Test Quality"].Values.Add(regressionSolution.TestRSquared);
       return base.Apply();
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SymbolGraph/FPGraph.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SymbolGraph/FPGraph.cs	(revision 10347)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SymbolGraph/FPGraph.cs	(revision 10347)
@@ -0,0 +1,63 @@
+﻿#region License Information
+/* HeuristicLab
+ * Copyright (C) 2002-2012 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
+ *
+ * This file is part of HeuristicLab.
+ *
+ * HeuristicLab is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * HeuristicLab is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
+ */
+#endregion
+
+using System.Collections.Generic;
+using System.Linq;
+using HeuristicLab.Core;
+using HeuristicLab.EvolutionTracking;
+using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
+
+namespace HeuristicLab.Problems.DataAnalysis.Symbolic {
+  [Item("Symbol graph", "A graph used to store the relationship between symbols in a population of individuals")]
+  [StorableClass]
+  public class FPGraph : DirectedGraph {
+    [Storable]
+    public Dictionary<int, List<SymbolNode>> Levels { get { return levels; } }
+    private Dictionary<int, List<SymbolNode>> levels = new Dictionary<int, List<SymbolNode>>();
+
+    public void AddNode(SymbolNode node, int level) {
+      if (levels.ContainsKey(level)) {
+        SymbolNode match = levels[level].Find(n => n.Label.Equals(node.Label));
+        if (match == null) {
+          levels[level].Add(node);
+        }
+      } else {
+        levels[level] = new List<SymbolNode> { node };
+      }
+      base.AddVertex(node);
+    }
+
+    public bool ContainsKey(string key, int level) {
+      return levels.ContainsKey(level) && levels[level].Select(n => n.Label).Contains(key);
+    }
+
+    public SymbolNode GetNode(string key, int level) {
+      SymbolNode node = null;
+      if (levels.ContainsKey(level))
+        node = levels[level].Find(n => n.Label.Equals(key));
+      return node;
+    }
+
+    void AddArc(SymbolNode source, SymbolNode target, double weight, object data = null) {
+      source.AddForwardArc(target, weight, data);
+    }
+  }
+}
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SymbolGraph/SymbolGraph.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SymbolGraph/SymbolGraph.cs	(revision 10347)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SymbolGraph/SymbolGraph.cs	(revision 10347)
@@ -0,0 +1,82 @@
+﻿#region License Information
+/* HeuristicLab
+ * Copyright (C) 2002-2012 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
+ *
+ * This file is part of HeuristicLab.
+ *
+ * HeuristicLab is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * HeuristicLab is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
+ */
+#endregion
+
+using System.Collections.Generic;
+using System.Linq;
+using HeuristicLab.Core;
+using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
+using HeuristicLab.EvolutionTracking;
+using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
+
+namespace HeuristicLab.Problems.DataAnalysis.Symbolic {
+  [Item("Symbol graph", "A graph used to store the relationship between symbols in a population of individuals")]
+  [StorableClass]
+  public class SymbolGraph : DirectedGraph {
+    [Storable]
+    private readonly Dictionary<string, SymbolNode> nodeMap = new Dictionary<string, SymbolNode>();
+
+    public void AddVertex(SymbolNode node) {
+      if (nodeMap.ContainsKey(node.Label)) return; // node already present? do nothing
+      nodeMap[node.Label] = node;
+      base.AddVertex(node);
+    }
+
+    public bool ContainsKey(string key) {
+      return nodeMap.ContainsKey(key);
+    }
+
+    public SymbolNode GetNode(string key) {
+      SymbolNode node;
+      nodeMap.TryGetValue(key, out node);
+      return node;
+    }
+
+    void AddArc(SymbolNode source, SymbolNode target, double weight, object data = null) {
+      source.AddForwardArc(target, weight, data);
+    }
+  }
+
+  [StorableClass]
+  public class SymbolNode : Vertex {
+    public ISymbol Symbol { get; set; }
+    public Dictionary<int, int> Positions { get; set; }
+    public double AverageArity { get; set; }
+
+    public new List<SymbolArc> InArcs {
+      get { return base.InArcs == null ? null : base.InArcs.Cast<SymbolArc>().ToList(); }
+    }
+
+    public new List<SymbolArc> OutArcs {
+      get { return base.OutArcs == null ? null : base.OutArcs.Cast<SymbolArc>().ToList(); }
+    }
+
+    public SymbolNode() {
+    }
+  }
+
+  public class SymbolArc : IArc {
+    public IVertex Source { get; set; }
+    public IVertex Target { get; set; }
+    public double Weight { get; set; }
+
+    public object Data { get; set; }
+  }
+}
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SymbolicDataAnalysisExpressionTreeMatching.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SymbolicDataAnalysisExpressionTreeMatching.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SymbolicDataAnalysisExpressionTreeMatching.cs	(revision 10347)
@@ -5,4 +5,5 @@
 using HeuristicLab.Core;
 using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
+using HeuristicLab.EvolutionTracking;
 using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
 using HeuristicLab.Problems.DataAnalysis.Symbolic;
@@ -79,14 +80,14 @@
   }
 
-  public class SymbolicExpressionTreeFragmentSimilarityComparer : IEqualityComparer<IFragment> {
+  public class SymbolicExpressionTreeFragmentSimilarityComparer : IEqualityComparer<IFragment<ISymbolicExpressionTreeNode>> {
     public SymbolicExpressionTreeNodeSimilarityComparer SimilarityComparer { get; set; }
 
-    public bool Equals(IFragment x, IFragment y) {
+    public bool Equals(IFragment<ISymbolicExpressionTreeNode> x, IFragment<ISymbolicExpressionTreeNode> y) {
       if (SimilarityComparer == null)
         throw new ArgumentNullException("SimilarityComparer needs to be initialized first.");
-      return x.Length == y.Length && SymbolicExpressionTreeMatching.Match(x.Root, y.Root, SimilarityComparer) == x.Length;
-    }
-
-    public int GetHashCode(IFragment fragment) {
+      return x.Root.GetLength() == y.Root.GetLength() && SymbolicExpressionTreeMatching.Match(x.Root, y.Root, SimilarityComparer) == x.Root.GetLength();
+    }
+
+    public int GetHashCode(IFragment<ISymbolicExpressionTreeNode> fragment) {
       return fragment.Root.Symbol.Name.ToLower().GetHashCode();
     }
@@ -162,5 +163,5 @@
 
 public static class SymbolicExpressionTreeMatching {
-  public static bool ContainsFragment(this ISymbolicExpressionTreeNode root, IFragment fragment, SymbolicExpressionTreeNodeSimilarityComparer comparer) {
+  public static bool ContainsFragment(this ISymbolicExpressionTreeNode root, IFragment<ISymbolicExpressionTreeNode> fragment, SymbolicExpressionTreeNodeSimilarityComparer comparer) {
     return FindMatches(root, fragment.Root, comparer).Any();
   }
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SymbolicDataAnalysisProblem.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SymbolicDataAnalysisProblem.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SymbolicDataAnalysisProblem.cs	(revision 10347)
@@ -28,4 +28,5 @@
 using HeuristicLab.Data;
 using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
+using HeuristicLab.EvolutionTracking;
 using HeuristicLab.Optimization;
 using HeuristicLab.Parameters;
@@ -355,11 +356,21 @@
       // add tracking analyzer
       foreach (var op in operators.OfType<SymbolicDataAnalysisGenealogyAnalyzer>()) {
+        //        op.BeforeCrossoverOperator = new SymbolicDataAnalysExpressionBeforeCrossoverOperator();
+        //        op.AfterCrossoverOperator = new SymbolicDataAnalysExpressionAfterCrossoverOperator();
+        op.BeforeCrossoverOperator = new BeforeCrossoverOperator<ISymbolicExpressionTree>();
+        op.AfterCrossoverOperator = new AfterCrossoverOperator<ISymbolicExpressionTree>();
+        op.BeforeManipulatorOperator = new BeforeManipulatorOperator<ISymbolicExpressionTree>();
+        op.AfterManipulatorOperator = new AfterManipulatorOperator<ISymbolicExpressionTree>();
         // get crossover parameter names
-        var crossover = operators.OfType<ISymbolicExpressionTreeCrossover>().First();
-        op.CrossoverParentsParameterName = crossover.ParentsParameter.Name;
-        op.CrossoverChildParameterName = crossover.ChildParameter.Name;
+        var crossover = operators.OfType<ISymbolicExpressionTreeCrossover>().FirstOrDefault();
+        if (crossover != null) {
+          op.CrossoverParentsParameterName = crossover.ParentsParameter.Name;
+          op.CrossoverChildParameterName = crossover.ChildParameter.Name;
+        }
         // get munipulator parameter names
-        var manipulator = operators.OfType<ISymbolicExpressionTreeManipulator>().First();
-        op.ManipulatorChildParameterName = manipulator.SymbolicExpressionTreeParameter.Name;
+        var manipulator = operators.OfType<ISymbolicExpressionTreeManipulator>().FirstOrDefault();
+        if (manipulator != null) {
+          op.ManipulatorChildParameterName = manipulator.SymbolicExpressionTreeParameter.Name;
+        }
       }
     }
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Tracking/SymbolicDataAnalysExpressionAfterCrossoverOperator.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Tracking/SymbolicDataAnalysExpressionAfterCrossoverOperator.cs	(revision 10347)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Tracking/SymbolicDataAnalysExpressionAfterCrossoverOperator.cs	(revision 10347)
@@ -0,0 +1,39 @@
+﻿using System;
+using System.Collections.Generic;
+using System.Linq;
+using HeuristicLab.Core;
+using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
+using HeuristicLab.EvolutionTracking;
+
+namespace HeuristicLab.Problems.DataAnalysis.Symbolic {
+  public class SymbolicDataAnalysExpressionAfterCrossoverOperator : AfterCrossoverOperator<ISymbolicExpressionTree> {
+    public override IOperation Apply() {
+      var childVertex = GenealogyGraph[ChildParameter.ActualValue].Last();
+      var arc0 = (IGenealogyGraphArc)childVertex.InArcs[0];
+      var arc1 = (IGenealogyGraphArc)childVertex.InArcs[1];
+      var nodes0 = (List<ISymbolicExpressionTreeNode>)arc0.Data;
+      var nodes1 = (List<ISymbolicExpressionTreeNode>)arc1.Data;
+      var childNodes = ChildParameter.ActualValue.IterateNodesBreadth().ToList();
+      IFragment<ISymbolicExpressionTreeNode> fragment = null;
+
+      for (int i = 0; i < Math.Min(nodes0.Count, childNodes.Count); ++i) {
+        if (nodes0[i] == childNodes[i]) continue;
+        fragment = new Fragment<ISymbolicExpressionTreeNode> {
+          Root = childNodes[i],
+          NewPos = i
+        };
+      }
+      if (fragment == null) throw new Exception("Could not determine fragment!");
+
+      for (int i = 0; i < nodes1.Count; ++i) {
+        if (nodes1[i] != fragment.Root) continue;
+        fragment.OldPos = i;
+      }
+
+      arc0.Data = null;
+      arc1.Data = fragment;
+
+      return base.Apply();
+    }
+  }
+}
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Tracking/SymbolicDataAnalysExpressionBeforeCrossoverOperator.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Tracking/SymbolicDataAnalysExpressionBeforeCrossoverOperator.cs	(revision 10347)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Tracking/SymbolicDataAnalysExpressionBeforeCrossoverOperator.cs	(revision 10347)
@@ -0,0 +1,23 @@
+﻿using System.Linq;
+using HeuristicLab.Core;
+using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
+using HeuristicLab.EvolutionTracking;
+
+namespace HeuristicLab.Problems.DataAnalysis.Symbolic {
+  public class SymbolicDataAnalysExpressionBeforeCrossoverOperator : BeforeCrossoverOperator<ISymbolicExpressionTree> {
+    public override IOperation Apply() {
+      var result = base.Apply();
+      var parents = ParentsParameter.ActualValue.ToList();
+      var childVertex = GenealogyGraph[parents[0]].Last(); // use the parent since it is actually the child before crossover (and the ChildParameter doesn't have a value yet)
+      //      var parentVertices = ExecutionContext.Scope.SubScopes.Select(s => CurrentGeneration[int.Parse(s.Name)]).ToList();
+
+      for (int i = 0; i < parents.Count; ++i) {
+        var nodes = parents[i].IterateNodesBreadth().ToList();
+        var arc = (IGenealogyGraphArc)childVertex.InArcs[i];
+        arc.Data = nodes;
+      }
+
+      return result;
+    }
+  }
+}
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Tracking/SymbolicDataAnalysisExpressionAfterManipulatorOperator.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Tracking/SymbolicDataAnalysisExpressionAfterManipulatorOperator.cs	(revision 10347)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Tracking/SymbolicDataAnalysisExpressionAfterManipulatorOperator.cs	(revision 10347)
@@ -0,0 +1,38 @@
+﻿using System;
+using System.Collections.Generic;
+using System.Linq;
+using HeuristicLab.Core;
+using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
+using HeuristicLab.EvolutionTracking;
+
+namespace HeuristicLab.Problems.DataAnalysis.Symbolic {
+  public class SymbolicDataAnalysisExpressionAfterManipulatorOperator : BeforeManipulatorOperator<ISymbolicExpressionTree> {
+    private readonly SymbolicExpressionTreeNodeSimilarityComparer comparer;
+
+    public SymbolicDataAnalysisExpressionAfterManipulatorOperator() {
+      comparer = new SymbolicExpressionTreeNodeSimilarityComparer {
+        MatchVariableNames = true,
+        MatchVariableWeights = true,
+        MatchConstantValues = true
+      };
+    }
+
+    public override IOperation Apply() {
+      var vChild = (IGenealogyGraphNode<ISymbolicExpressionTree>)GenealogyGraph[ChildParameter.ActualValue].First();
+      var nodesBefore = (List<ISymbolicExpressionTreeNode>)vChild.InArcs[0].Data;
+      var nodesAfter = ChildParameter.ActualValue.IterateNodesBreadth().ToList();
+      IFragment<ISymbolicExpressionTreeNode> fragment = null;
+
+      for (int i = 0; i < Math.Min(nodesAfter.Count, nodesBefore.Count); ++i) {
+        if (comparer.Equals(nodesAfter[i], nodesBefore[i])) continue;
+        fragment = new Fragment<ISymbolicExpressionTreeNode> {
+          Root = nodesAfter[i],
+          NewPos = i
+        };
+      }
+
+      vChild.InArcs[0].Data = fragment;
+      return base.Apply();
+    }
+  }
+}
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Tracking/SymbolicDataAnalysisExpressionBeforeManipulatorOperator.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Tracking/SymbolicDataAnalysisExpressionBeforeManipulatorOperator.cs	(revision 10347)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/Tracking/SymbolicDataAnalysisExpressionBeforeManipulatorOperator.cs	(revision 10347)
@@ -0,0 +1,17 @@
+﻿using System.Linq;
+using HeuristicLab.Core;
+using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
+using HeuristicLab.EvolutionTracking;
+
+namespace HeuristicLab.Problems.DataAnalysis.Symbolic {
+  public class SymbolicDataAnalysisExpressionBeforeManipulatorOperator : BeforeManipulatorOperator<ISymbolicExpressionTree> {
+    public override IOperation Apply() {
+      var result = base.Apply();
+
+      var vChild = (IGenealogyGraphNode<ISymbolicExpressionTree>)GenealogyGraph[ChildParameter.ActualValue].Last();
+      vChild.InArcs[0].Data = vChild.Content.IterateNodesBreadth().ToList();
+
+      return result;
+    }
+  }
+}
Index: branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.TravelingSalesman/3.3/TravelingSalesmanProblem.cs
===================================================================
--- branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.TravelingSalesman/3.3/TravelingSalesmanProblem.cs	(revision 10345)
+++ branches/HeuristicLab.EvolutionTracking/HeuristicLab.Problems.TravelingSalesman/3.3/TravelingSalesmanProblem.cs	(revision 10347)
@@ -29,4 +29,5 @@
 using HeuristicLab.Data;
 using HeuristicLab.Encodings.PermutationEncoding;
+using HeuristicLab.EvolutionTracking;
 using HeuristicLab.Optimization;
 using HeuristicLab.Parameters;
@@ -386,8 +387,12 @@
       if (TSPGenealogyAnalyzer != null) {
         if (TSPCrossover != null) {
+          TSPGenealogyAnalyzer.BeforeCrossoverOperator = new BeforeCrossoverOperator<Permutation>();
+          TSPGenealogyAnalyzer.AfterCrossoverOperator = new AfterCrossoverOperator<Permutation>();
           TSPGenealogyAnalyzer.CrossoverParentsParameterName = TSPCrossover.ParentsParameter.Name;
           TSPGenealogyAnalyzer.CrossoverChildParameterName = TSPCrossover.ChildParameter.Name;
         }
         if (TSPManipulator != null) {
+          TSPGenealogyAnalyzer.BeforeManipulatorOperator = new BeforeManipulatorOperator<Permutation>();
+          TSPGenealogyAnalyzer.AfterManipulatorOperator = new AfterManipulatorOperator<Permutation>();
           TSPGenealogyAnalyzer.ManipulatorChildParameterName = TSPManipulator.PermutationParameter.Name;
         }
