Free cookie consent management tool by TermsFeed Policy Generator

source: branches/DataAnalysis/HeuristicLab.Problems.DataAnalysis.MultiVariate.TimeSeriesPrognosis/3.3/Symbolic/Evaluators/SymbolicTimeSeriesPrognosisScaledNormalizedMseEvaluator.cs @ 5275

Last change on this file since 5275 was 5275, checked in by gkronber, 13 years ago

Merged changes from trunk to data analysis exploration branch and added fractional distance metric evaluator. #1142

File size: 9.8 KB
Line 
1#region License Information
2/* HeuristicLab
3 * Copyright (C) 2002-2010 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
4 *
5 * This file is part of HeuristicLab.
6 *
7 * HeuristicLab is free software: you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation, either version 3 of the License, or
10 * (at your option) any later version.
11 *
12 * HeuristicLab is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
19 */
20#endregion
21
22using System;
23using System.Linq;
24using HeuristicLab.Common;
25using HeuristicLab.Core;
26using HeuristicLab.Data;
27using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
28using HeuristicLab.Problems.DataAnalysis.SupportVectorMachine;
29using HeuristicLab.Problems.DataAnalysis;
30using HeuristicLab.Problems.DataAnalysis.Evaluators;
31using HeuristicLab.Parameters;
32using HeuristicLab.Optimization;
33using HeuristicLab.Operators;
34using HeuristicLab.Problems.DataAnalysis.Regression.Symbolic;
35using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;
36using System.Collections.Generic;
37using HeuristicLab.Problems.DataAnalysis.Regression;
38using HeuristicLab.Problems.DataAnalysis.MultiVariate.TimeSeriesPrognosis.Symbolic.Interfaces;
39using HeuristicLab.Problems.DataAnalysis.MultiVariate.Evaluators;
40
41namespace HeuristicLab.Problems.DataAnalysis.MultiVariate.TimeSeriesPrognosis.Symbolic.Evaluators {
42  [Item("SymbolicTimeSeriesPrognosisScaledNormalizedMseEvaluator", "")]
43  [StorableClass]
44  public class SymbolicTimeSeriesPrognosisScaledNormalizedMseEvaluator : SymbolicTimeSeriesPrognosisEvaluator {
45
46    [StorableConstructor]
47    protected SymbolicTimeSeriesPrognosisScaledNormalizedMseEvaluator(bool deserializing) : base(deserializing) { }
48    protected SymbolicTimeSeriesPrognosisScaledNormalizedMseEvaluator(SymbolicTimeSeriesPrognosisScaledNormalizedMseEvaluator original, Cloner cloner)
49      : base(original, cloner) {
50    }
51    public SymbolicTimeSeriesPrognosisScaledNormalizedMseEvaluator()
52      : base() {
53    }
54    public override IDeepCloneable Clone(Cloner cloner) {
55      return new SymbolicTimeSeriesPrognosisScaledNormalizedMseEvaluator(this, cloner);
56    }
57    public override double Evaluate(SymbolicExpressionTree tree, MultiVariateDataAnalysisProblemData problemData, ISymbolicTimeSeriesExpressionInterpreter interpreter, IEnumerable<int> rows, int predictionHorizon, DoubleArray lowerEstimationLimit, DoubleArray upperEstimationLimit) {
58      return Calculate(tree, problemData, interpreter, rows, predictionHorizon, lowerEstimationLimit, upperEstimationLimit);
59    }
60
61    public static double Calculate(SymbolicExpressionTree tree, MultiVariateDataAnalysisProblemData problemData, ISymbolicTimeSeriesExpressionInterpreter interpreter, IEnumerable<int> rows, int predictionHorizon, DoubleArray lowerEstimationLimit, DoubleArray upperEstimationLimit) {
62      double[] alpha, beta;
63      double quality;
64
65      Dataset dataset = problemData.Dataset;
66      // calculate scaling parameters based on one-step-predictions
67      IEnumerable<string> selectedTargetVariables = (from item in problemData.TargetVariables
68                                                     where problemData.TargetVariables.ItemChecked(item)
69                                                     select item.Value).ToArray();
70      int dimension = selectedTargetVariables.Count();
71
72      IEnumerable<int> selectedTargetVariableIndexes = (from targetVariable in selectedTargetVariables
73                                                        select dataset.GetVariableIndex(targetVariable)).ToArray();
74      IEnumerable<IEnumerable<double>> oneStepPredictions =
75        interpreter.GetSymbolicExpressionTreeValues(tree, problemData.Dataset, selectedTargetVariables, rows, 1).Cast<IEnumerable<double>>();
76      IEnumerable<IEnumerable<double>> originalValues = from row in rows
77                                                        select (from targetVariableIndex in selectedTargetVariableIndexes
78                                                                select dataset[row, targetVariableIndex]);
79      alpha = new double[dimension];
80      beta = new double[dimension];
81
82      CalculateScalingParameters(originalValues, oneStepPredictions, ref beta, ref alpha);
83
84      // calculate the quality for the full horizon
85      quality = CalculateWithScaling(tree, problemData, interpreter,
86        rows, predictionHorizon,
87        lowerEstimationLimit, upperEstimationLimit,
88        beta, alpha);
89      return quality;
90    }
91
92    public static double CalculateWithScaling(SymbolicExpressionTree tree, MultiVariateDataAnalysisProblemData problemData,
93      ISymbolicTimeSeriesExpressionInterpreter interpreter,
94      IEnumerable<int> rows, int predictionHorizon,
95      DoubleArray lowerEstimationLimit, DoubleArray upperEstimationLimit,
96      double[] beta, double[] alpha) {
97      Dataset dataset = problemData.Dataset;
98      IEnumerable<string> selectedTargetVariables = (from targetVariable in problemData.TargetVariables
99                                                     where problemData.TargetVariables.ItemChecked(targetVariable)
100                                                     select targetVariable.Value).ToArray();
101      IEnumerable<int> selectedTargetVariableIndexes = (from targetVariable in selectedTargetVariables
102                                                        select dataset.GetVariableIndex(targetVariable)).ToArray();
103
104      IEnumerable<double[]> estimatedValues =
105        interpreter.GetScaledSymbolicExpressionTreeValues(tree, dataset, selectedTargetVariables,
106        rows, predictionHorizon, beta, alpha);
107
108      IEnumerable<IEnumerable<double>> originalValues = from row in rows
109                                                        from step in Enumerable.Range(0, predictionHorizon)
110                                                        select (from targetVariableIndex in selectedTargetVariableIndexes
111                                                                select dataset[row + step, targetVariableIndex]);
112
113      var evaluator = new OnlineMultiVariateEvaluator<OnlineNormalizedMeanSquaredErrorEvaluator>();
114
115      var estimatedValuesEnumerator = estimatedValues.GetEnumerator();
116      var originalValuesEnumerator = originalValues.GetEnumerator();
117      while (originalValuesEnumerator.MoveNext() & estimatedValuesEnumerator.MoveNext()) {
118        IEnumerable<double> original = originalValuesEnumerator.Current;
119        double[] estimated = estimatedValuesEnumerator.Current;
120        for (int i = 0; i < estimated.Length; i++) {
121          if (double.IsNaN(estimated[i])) estimated[i] = upperEstimationLimit[i];
122          else estimated[i] = Math.Min(upperEstimationLimit[i], Math.Max(lowerEstimationLimit[i], estimated[i]));
123        }
124        evaluator.Add(original, estimated);
125      }
126
127      double quality = evaluator.Value;
128      return quality;
129    }
130
131    public static void CalculateScalingParameters(IEnumerable<IEnumerable<double>> originalValues, IEnumerable<IEnumerable<double>> estimatedValues, ref double[] beta, ref double[] alpha) {
132      List<OnlineLinearScalingCalculator> linearScalingCalculators = new List<OnlineLinearScalingCalculator>();
133      // initialize lists
134      int dimension = originalValues.First().Count();
135      for (int i = 0; i < dimension; i++) {
136        linearScalingCalculators.Add(new OnlineLinearScalingCalculator());
137      }
138
139      var estimatedEnumerator = estimatedValues.GetEnumerator();
140      var originalEnumerator = originalValues.GetEnumerator();
141      // foreach row vector in both series
142      while (estimatedEnumerator.MoveNext() & originalEnumerator.MoveNext()) {
143        IEnumerable<double> original = originalEnumerator.Current;
144        IEnumerable<double> estimated = estimatedEnumerator.Current;
145        var originalComponentValuesEnumerator = original.GetEnumerator();
146        var estimatedComponentValuesEnumerator = estimated.GetEnumerator();
147
148        int component = 0;
149        // for each component in both row vectors
150        while (originalComponentValuesEnumerator.MoveNext() & estimatedComponentValuesEnumerator.MoveNext() && component < dimension) {
151          if (IsValidValue(originalComponentValuesEnumerator.Current) && IsValidValue(estimatedComponentValuesEnumerator.Current)) {
152            linearScalingCalculators[component].Add(originalComponentValuesEnumerator.Current, estimatedComponentValuesEnumerator.Current);
153          }
154          component++;
155        }
156        // check if both row vectors are finished
157        if (originalComponentValuesEnumerator.MoveNext() | estimatedComponentValuesEnumerator.MoveNext() || component < dimension) {
158          throw new ArgumentException("Number of elements in original and estimated row vectors does not match.");
159        }
160      }
161
162      // check if both series are finished
163      if (estimatedEnumerator.MoveNext() || originalEnumerator.MoveNext())
164        throw new InvalidOperationException("Number of elements in estimated and original series doesn't match.");
165
166      // get alpha and beta for each component
167      for (int component = 0; component < dimension; component++) {
168        alpha[component] = linearScalingCalculators[component].Alpha;
169        beta[component] = linearScalingCalculators[component].Beta;
170      }
171    }
172
173    private static bool IsValidValue(double d) {
174      return !double.IsInfinity(d) && !double.IsNaN(d) && d > -1.0E07 && d < 1.0E07;  // don't consider very large or very small values for scaling
175    }
176  }
177}
Note: See TracBrowser for help on using the repository browser.