Index: trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/HeuristicLab.Problems.DataAnalysis-3.4.csproj
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/HeuristicLab.Problems.DataAnalysis-3.4.csproj	(revision 6587)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/HeuristicLab.Problems.DataAnalysis-3.4.csproj	(revision 6588)
@@ -136,4 +136,5 @@
     </Compile>
     <Compile Include="Interfaces\Regression\IRegressionEnsembleSolution.cs" />
+    <Compile Include="Implementation\Regression\RegressionSolutionBase.cs" />
     <Compile Include="OnlineCalculators\OnlineLinearScalingParameterCalculator.cs" />
     <Compile Include="Implementation\Classification\DiscriminantFunctionClassificationModel.cs" />
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/DataAnalysisSolution.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/DataAnalysisSolution.cs	(revision 6587)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/DataAnalysisSolution.cs	(revision 6588)
@@ -80,6 +80,6 @@
       name = ItemName;
       description = ItemDescription;
-      Add(new Result(ModelResultName, "The symbolic data analysis model.", model));
-      Add(new Result(ProblemDataResultName, "The symbolic data analysis problem data.", problemData));
+      Add(new Result(ModelResultName, "The data analysis model.", model));
+      Add(new Result(ProblemDataResultName, "The data analysis problem data.", problemData));
 
       problemData.Changed += new EventHandler(ProblemData_Changed);
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Regression/RegressionEnsembleSolution.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Regression/RegressionEnsembleSolution.cs	(revision 6587)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Regression/RegressionEnsembleSolution.cs	(revision 6588)
@@ -20,11 +20,11 @@
 #endregion
 
+using System;
 using System.Collections.Generic;
 using System.Linq;
 using HeuristicLab.Common;
 using HeuristicLab.Core;
+using HeuristicLab.Data;
 using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
-using System;
-using HeuristicLab.Data;
 
 namespace HeuristicLab.Problems.DataAnalysis {
@@ -80,4 +80,8 @@
     public override IDeepCloneable Clone(Cloner cloner) {
       return new RegressionEnsembleSolution(this, cloner);
+    }
+
+    protected override void RecalculateResults() {
+      CalculateResults();
     }
 
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Regression/RegressionSolution.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Regression/RegressionSolution.cs	(revision 6587)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Regression/RegressionSolution.cs	(revision 6588)
@@ -23,6 +23,4 @@
 using System.Linq;
 using HeuristicLab.Common;
-using HeuristicLab.Data;
-using HeuristicLab.Optimization;
 using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
 
@@ -32,65 +30,5 @@
   /// </summary>
   [StorableClass]
-  public class RegressionSolution : DataAnalysisSolution, IRegressionSolution {
-    private const string TrainingMeanSquaredErrorResultName = "Mean squared error (training)";
-    private const string TestMeanSquaredErrorResultName = "Mean squared error (test)";
-    private const string TrainingSquaredCorrelationResultName = "Pearson's R² (training)";
-    private const string TestSquaredCorrelationResultName = "Pearson's R² (test)";
-    private const string TrainingRelativeErrorResultName = "Average relative error (training)";
-    private const string TestRelativeErrorResultName = "Average relative error (test)";
-    private const string TrainingNormalizedMeanSquaredErrorResultName = "Normalized mean squared error (training)";
-    private const string TestNormalizedMeanSquaredErrorResultName = "Normalized mean squared error (test)";
-
-    public new IRegressionModel Model {
-      get { return (IRegressionModel)base.Model; }
-      protected set { base.Model = value; }
-    }
-
-    public new IRegressionProblemData ProblemData {
-      get { return (IRegressionProblemData)base.ProblemData; }
-      protected set { base.ProblemData = value; }
-    }
-
-    public double TrainingMeanSquaredError {
-      get { return ((DoubleValue)this[TrainingMeanSquaredErrorResultName].Value).Value; }
-      private set { ((DoubleValue)this[TrainingMeanSquaredErrorResultName].Value).Value = value; }
-    }
-
-    public double TestMeanSquaredError {
-      get { return ((DoubleValue)this[TestMeanSquaredErrorResultName].Value).Value; }
-      private set { ((DoubleValue)this[TestMeanSquaredErrorResultName].Value).Value = value; }
-    }
-
-    public double TrainingRSquared {
-      get { return ((DoubleValue)this[TrainingSquaredCorrelationResultName].Value).Value; }
-      private set { ((DoubleValue)this[TrainingSquaredCorrelationResultName].Value).Value = value; }
-    }
-
-    public double TestRSquared {
-      get { return ((DoubleValue)this[TestSquaredCorrelationResultName].Value).Value; }
-      private set { ((DoubleValue)this[TestSquaredCorrelationResultName].Value).Value = value; }
-    }
-
-    public double TrainingRelativeError {
-      get { return ((DoubleValue)this[TrainingRelativeErrorResultName].Value).Value; }
-      private set { ((DoubleValue)this[TrainingRelativeErrorResultName].Value).Value = value; }
-    }
-
-    public double TestRelativeError {
-      get { return ((DoubleValue)this[TestRelativeErrorResultName].Value).Value; }
-      private set { ((DoubleValue)this[TestRelativeErrorResultName].Value).Value = value; }
-    }
-
-    public double TrainingNormalizedMeanSquaredError {
-      get { return ((DoubleValue)this[TrainingNormalizedMeanSquaredErrorResultName].Value).Value; }
-      private set { ((DoubleValue)this[TrainingNormalizedMeanSquaredErrorResultName].Value).Value = value; }
-    }
-
-    public double TestNormalizedMeanSquaredError {
-      get { return ((DoubleValue)this[TestNormalizedMeanSquaredErrorResultName].Value).Value; }
-      private set { ((DoubleValue)this[TestNormalizedMeanSquaredErrorResultName].Value).Value = value; }
-    }
-
-
+  public abstract class RegressionSolution : RegressionSolutionBase {
     [StorableConstructor]
     protected RegressionSolution(bool deserializing) : base(deserializing) { }
@@ -98,73 +36,19 @@
       : base(original, cloner) {
     }
-    public RegressionSolution(IRegressionModel model, IRegressionProblemData problemData)
+    protected RegressionSolution(IRegressionModel model, IRegressionProblemData problemData)
       : base(model, problemData) {
-      Add(new Result(TrainingMeanSquaredErrorResultName, "Mean of squared errors of the model on the training partition", new DoubleValue()));
-      Add(new Result(TestMeanSquaredErrorResultName, "Mean of squared errors of the model on the test partition", new DoubleValue()));
-      Add(new Result(TrainingSquaredCorrelationResultName, "Squared Pearson's correlation coefficient of the model output and the actual values on the training partition", new DoubleValue()));
-      Add(new Result(TestSquaredCorrelationResultName, "Squared Pearson's correlation coefficient of the model output and the actual values on the test partition", new DoubleValue()));
-      Add(new Result(TrainingRelativeErrorResultName, "Average of the relative errors of the model output and the actual values on the training partition", new PercentValue()));
-      Add(new Result(TestRelativeErrorResultName, "Average of the relative errors of the model output and the actual values on the test partition", new PercentValue()));
-      Add(new Result(TrainingNormalizedMeanSquaredErrorResultName, "Normalized mean of squared errors of the model on the training partition", new DoubleValue()));
-      Add(new Result(TestNormalizedMeanSquaredErrorResultName, "Normalized mean of squared errors of the model on the test partition", new DoubleValue()));
-
-      CalculateResults();
     }
 
-    public override IDeepCloneable Clone(Cloner cloner) {
-      return new RegressionSolution(this, cloner);
+    public override IEnumerable<double> EstimatedValues {
+      get { return GetEstimatedValues(Enumerable.Range(0, ProblemData.Dataset.Rows)); }
+    }
+    public override IEnumerable<double> EstimatedTrainingValues {
+      get { return GetEstimatedValues(ProblemData.TrainingIndizes); }
+    }
+    public override IEnumerable<double> EstimatedTestValues {
+      get { return GetEstimatedValues(ProblemData.TestIndizes); }
     }
 
-    protected override void RecalculateResults() {
-      CalculateResults();
-    }
-
-    private void CalculateResults() {
-      double[] estimatedTrainingValues = EstimatedTrainingValues.ToArray(); // cache values
-      IEnumerable<double> originalTrainingValues = ProblemData.Dataset.GetEnumeratedVariableValues(ProblemData.TargetVariable, ProblemData.TrainingIndizes);
-      double[] estimatedTestValues = EstimatedTestValues.ToArray(); // cache values
-      IEnumerable<double> originalTestValues = ProblemData.Dataset.GetEnumeratedVariableValues(ProblemData.TargetVariable, ProblemData.TestIndizes);
-
-      OnlineCalculatorError errorState;
-      double trainingMSE = OnlineMeanSquaredErrorCalculator.Calculate(estimatedTrainingValues, originalTrainingValues, out errorState);
-      TrainingMeanSquaredError = errorState == OnlineCalculatorError.None ? trainingMSE : double.NaN;
-      double testMSE = OnlineMeanSquaredErrorCalculator.Calculate(estimatedTestValues, originalTestValues, out errorState);
-      TestMeanSquaredError = errorState == OnlineCalculatorError.None ? testMSE : double.NaN;
-
-      double trainingR2 = OnlinePearsonsRSquaredCalculator.Calculate(estimatedTrainingValues, originalTrainingValues, out errorState);
-      TrainingRSquared = errorState == OnlineCalculatorError.None ? trainingR2 : double.NaN;
-      double testR2 = OnlinePearsonsRSquaredCalculator.Calculate(estimatedTestValues, originalTestValues, out errorState);
-      TestRSquared = errorState == OnlineCalculatorError.None ? testR2 : double.NaN;
-
-      double trainingRelError = OnlineMeanAbsolutePercentageErrorCalculator.Calculate(estimatedTrainingValues, originalTrainingValues, out errorState);
-      TrainingRelativeError = errorState == OnlineCalculatorError.None ? trainingRelError : double.NaN;
-      double testRelError = OnlineMeanAbsolutePercentageErrorCalculator.Calculate(estimatedTestValues, originalTestValues, out errorState);
-      TestRelativeError = errorState == OnlineCalculatorError.None ? testRelError : double.NaN;
-
-      double trainingNMSE = OnlineNormalizedMeanSquaredErrorCalculator.Calculate(estimatedTrainingValues, originalTrainingValues, out errorState);
-      TrainingNormalizedMeanSquaredError = errorState == OnlineCalculatorError.None ? trainingNMSE : double.NaN;
-      double testNMSE = OnlineNormalizedMeanSquaredErrorCalculator.Calculate(estimatedTestValues, originalTestValues, out errorState);
-      TestNormalizedMeanSquaredError = errorState == OnlineCalculatorError.None ? testNMSE : double.NaN;
-    }
-
-    public virtual IEnumerable<double> EstimatedValues {
-      get {
-        return GetEstimatedValues(Enumerable.Range(0, ProblemData.Dataset.Rows));
-      }
-    }
-
-    public virtual IEnumerable<double> EstimatedTrainingValues {
-      get {
-        return GetEstimatedValues(ProblemData.TrainingIndizes);
-      }
-    }
-
-    public virtual IEnumerable<double> EstimatedTestValues {
-      get {
-        return GetEstimatedValues(ProblemData.TestIndizes);
-      }
-    }
-
-    public virtual IEnumerable<double> GetEstimatedValues(IEnumerable<int> rows) {
+    public override IEnumerable<double> GetEstimatedValues(IEnumerable<int> rows) {
       return Model.GetEstimatedValues(ProblemData.Dataset, rows);
     }
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Regression/RegressionSolutionBase.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Regression/RegressionSolutionBase.cs	(revision 6588)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Regression/RegressionSolutionBase.cs	(revision 6588)
@@ -0,0 +1,139 @@
+﻿#region License Information
+/* HeuristicLab
+ * Copyright (C) 2002-2011 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.Common;
+using HeuristicLab.Data;
+using HeuristicLab.Optimization;
+using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
+
+namespace HeuristicLab.Problems.DataAnalysis {
+  /// <summary>
+  /// Represents a regression data analysis solution
+  /// </summary>
+  [StorableClass]
+  public abstract class RegressionSolutionBase : DataAnalysisSolution, IRegressionSolution {
+    private const string TrainingMeanSquaredErrorResultName = "Mean squared error (training)";
+    private const string TestMeanSquaredErrorResultName = "Mean squared error (test)";
+    private const string TrainingSquaredCorrelationResultName = "Pearson's R² (training)";
+    private const string TestSquaredCorrelationResultName = "Pearson's R² (test)";
+    private const string TrainingRelativeErrorResultName = "Average relative error (training)";
+    private const string TestRelativeErrorResultName = "Average relative error (test)";
+    private const string TrainingNormalizedMeanSquaredErrorResultName = "Normalized mean squared error (training)";
+    private const string TestNormalizedMeanSquaredErrorResultName = "Normalized mean squared error (test)";
+
+    public new IRegressionModel Model {
+      get { return (IRegressionModel)base.Model; }
+      protected set { base.Model = value; }
+    }
+
+    public new IRegressionProblemData ProblemData {
+      get { return (IRegressionProblemData)base.ProblemData; }
+      protected set { base.ProblemData = value; }
+    }
+
+    public abstract IEnumerable<double> EstimatedValues { get; }
+    public abstract IEnumerable<double> EstimatedTrainingValues { get; }
+    public abstract IEnumerable<double> EstimatedTestValues { get; }
+    public abstract IEnumerable<double> GetEstimatedValues(IEnumerable<int> rows);
+
+    #region Results
+    public double TrainingMeanSquaredError {
+      get { return ((DoubleValue)this[TrainingMeanSquaredErrorResultName].Value).Value; }
+      private set { ((DoubleValue)this[TrainingMeanSquaredErrorResultName].Value).Value = value; }
+    }
+    public double TestMeanSquaredError {
+      get { return ((DoubleValue)this[TestMeanSquaredErrorResultName].Value).Value; }
+      private set { ((DoubleValue)this[TestMeanSquaredErrorResultName].Value).Value = value; }
+    }
+    public double TrainingRSquared {
+      get { return ((DoubleValue)this[TrainingSquaredCorrelationResultName].Value).Value; }
+      private set { ((DoubleValue)this[TrainingSquaredCorrelationResultName].Value).Value = value; }
+    }
+    public double TestRSquared {
+      get { return ((DoubleValue)this[TestSquaredCorrelationResultName].Value).Value; }
+      private set { ((DoubleValue)this[TestSquaredCorrelationResultName].Value).Value = value; }
+    }
+    public double TrainingRelativeError {
+      get { return ((DoubleValue)this[TrainingRelativeErrorResultName].Value).Value; }
+      private set { ((DoubleValue)this[TrainingRelativeErrorResultName].Value).Value = value; }
+    }
+    public double TestRelativeError {
+      get { return ((DoubleValue)this[TestRelativeErrorResultName].Value).Value; }
+      private set { ((DoubleValue)this[TestRelativeErrorResultName].Value).Value = value; }
+    }
+    public double TrainingNormalizedMeanSquaredError {
+      get { return ((DoubleValue)this[TrainingNormalizedMeanSquaredErrorResultName].Value).Value; }
+      private set { ((DoubleValue)this[TrainingNormalizedMeanSquaredErrorResultName].Value).Value = value; }
+    }
+    public double TestNormalizedMeanSquaredError {
+      get { return ((DoubleValue)this[TestNormalizedMeanSquaredErrorResultName].Value).Value; }
+      private set { ((DoubleValue)this[TestNormalizedMeanSquaredErrorResultName].Value).Value = value; }
+    }
+    #endregion
+
+    [StorableConstructor]
+    protected RegressionSolutionBase(bool deserializing) : base(deserializing) { }
+    protected RegressionSolutionBase(RegressionSolutionBase original, Cloner cloner)
+      : base(original, cloner) {
+    }
+    protected RegressionSolutionBase(IRegressionModel model, IRegressionProblemData problemData)
+      : base(model, problemData) {
+      Add(new Result(TrainingMeanSquaredErrorResultName, "Mean of squared errors of the model on the training partition", new DoubleValue()));
+      Add(new Result(TestMeanSquaredErrorResultName, "Mean of squared errors of the model on the test partition", new DoubleValue()));
+      Add(new Result(TrainingSquaredCorrelationResultName, "Squared Pearson's correlation coefficient of the model output and the actual values on the training partition", new DoubleValue()));
+      Add(new Result(TestSquaredCorrelationResultName, "Squared Pearson's correlation coefficient of the model output and the actual values on the test partition", new DoubleValue()));
+      Add(new Result(TrainingRelativeErrorResultName, "Average of the relative errors of the model output and the actual values on the training partition", new PercentValue()));
+      Add(new Result(TestRelativeErrorResultName, "Average of the relative errors of the model output and the actual values on the test partition", new PercentValue()));
+      Add(new Result(TrainingNormalizedMeanSquaredErrorResultName, "Normalized mean of squared errors of the model on the training partition", new DoubleValue()));
+      Add(new Result(TestNormalizedMeanSquaredErrorResultName, "Normalized mean of squared errors of the model on the test partition", new DoubleValue()));
+    }
+
+    protected void CalculateResults() {
+      double[] estimatedTrainingValues = EstimatedTrainingValues.ToArray(); // cache values
+      double[] originalTrainingValues = ProblemData.Dataset.GetEnumeratedVariableValues(ProblemData.TargetVariable, ProblemData.TrainingIndizes).ToArray();
+      double[] estimatedTestValues = EstimatedTestValues.ToArray(); // cache values
+      double[] originalTestValues = ProblemData.Dataset.GetEnumeratedVariableValues(ProblemData.TargetVariable, ProblemData.TestIndizes).ToArray();
+
+      OnlineCalculatorError errorState;
+      double trainingMSE = OnlineMeanSquaredErrorCalculator.Calculate(estimatedTrainingValues, originalTrainingValues, out errorState);
+      TrainingMeanSquaredError = errorState == OnlineCalculatorError.None ? trainingMSE : double.NaN;
+      double testMSE = OnlineMeanSquaredErrorCalculator.Calculate(estimatedTestValues, originalTestValues, out errorState);
+      TestMeanSquaredError = errorState == OnlineCalculatorError.None ? testMSE : double.NaN;
+
+      double trainingR2 = OnlinePearsonsRSquaredCalculator.Calculate(estimatedTrainingValues, originalTrainingValues, out errorState);
+      TrainingRSquared = errorState == OnlineCalculatorError.None ? trainingR2 : double.NaN;
+      double testR2 = OnlinePearsonsRSquaredCalculator.Calculate(estimatedTestValues, originalTestValues, out errorState);
+      TestRSquared = errorState == OnlineCalculatorError.None ? testR2 : double.NaN;
+
+      double trainingRelError = OnlineMeanAbsolutePercentageErrorCalculator.Calculate(estimatedTrainingValues, originalTrainingValues, out errorState);
+      TrainingRelativeError = errorState == OnlineCalculatorError.None ? trainingRelError : double.NaN;
+      double testRelError = OnlineMeanAbsolutePercentageErrorCalculator.Calculate(estimatedTestValues, originalTestValues, out errorState);
+      TestRelativeError = errorState == OnlineCalculatorError.None ? testRelError : double.NaN;
+
+      double trainingNMSE = OnlineNormalizedMeanSquaredErrorCalculator.Calculate(estimatedTrainingValues, originalTrainingValues, out errorState);
+      TrainingNormalizedMeanSquaredError = errorState == OnlineCalculatorError.None ? trainingNMSE : double.NaN;
+      double testNMSE = OnlineNormalizedMeanSquaredErrorCalculator.Calculate(estimatedTestValues, originalTestValues, out errorState);
+      TestNormalizedMeanSquaredError = errorState == OnlineCalculatorError.None ? testNMSE : double.NaN;
+    }
+  }
+}
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Interfaces/Regression/IRegressionSolution.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Interfaces/Regression/IRegressionSolution.cs	(revision 6587)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Interfaces/Regression/IRegressionSolution.cs	(revision 6588)
@@ -37,4 +37,6 @@
     double TrainingRelativeError { get; }
     double TestRelativeError { get; }
+    double TrainingNormalizedMeanSquaredError { get; }
+    double TestNormalizedMeanSquaredError { get; }
   }
 }
