Changeset 10720
- Timestamp:
- 04/03/14 11:06:14 (11 years ago)
- Location:
- branches/Sliding Window GP
- Files:
-
- 6 edited
Legend:
- Unmodified
- Added
- Removed
-
branches/Sliding Window GP/HeuristicLab.Problems.DataAnalysis.Symbolic.Regression/3.4/SlidingWindow/GenerationalRegressionSlidingWindowAnalyzer.cs
r10681 r10720 41 41 public GenerationalRegressionSlidingWindowAnalyzer() { } 42 42 public override IOperation Apply() { 43 if (!ResultCollection.ContainsKey( "Best Solutions")) {44 ResultCollection.Add(new Result( "Best Solutions", new SlidingWindowBestRegressionSolutionsCollection()));43 if (!ResultCollection.ContainsKey(BestSlidingWindowSolutionsResultName)) { 44 ResultCollection.Add(new Result(BestSlidingWindowSolutionsResultName, new SlidingWindowBestRegressionSolutionsCollection())); 45 45 } 46 46 return base.Apply(); -
branches/Sliding Window GP/HeuristicLab.Problems.DataAnalysis.Symbolic.Regression/3.4/SlidingWindow/OffspringSelectionRegressionSlidingWindowAnalyzer.cs
r10681 r10720 41 41 public OffspringSelectionRegressionSlidingWindowAnalyzer() { } 42 42 public override IOperation Apply() { 43 if (!ResultCollection.ContainsKey( "Best Solutions")) {44 ResultCollection.Add(new Result( "Best Solutions", new SlidingWindowBestRegressionSolutionsCollection()));43 if (!ResultCollection.ContainsKey(BestSlidingWindowSolutionsResultName)) { 44 ResultCollection.Add(new Result(BestSlidingWindowSolutionsResultName, new SlidingWindowBestRegressionSolutionsCollection())); 45 45 } 46 46 return base.Apply(); -
branches/Sliding Window GP/HeuristicLab.Problems.DataAnalysis.Symbolic.Views/3.4/SlidingWindowBestSolutionsCollectionHeatMapView.cs
r10686 r10720 21 21 22 22 using System; 23 using System.Co llections.Generic;23 using System.ComponentModel; 24 24 using System.Linq; 25 25 using System.Windows.Forms; 26 26 using HeuristicLab.Analysis; 27 27 using HeuristicLab.Core.Views; 28 using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;29 28 using HeuristicLab.MainForm; 30 29 using HeuristicLab.Optimization; … … 39 38 set { base.Content = value; } 40 39 } 40 41 protected override void OnContentChanged() { 42 base.OnContentChanged(); 43 if (Content != null) { 44 if (Content.SlidingWindowQualities != null) { 45 SetHeatmapContent(Content.SlidingWindowQualities); 46 } else if (!Content.QualitiesCalculationInProgress) { 47 progress.Start("Calculating best solution qualities..."); 48 Content.CalculateQualities(); 49 } 50 } 51 } 52 53 private readonly IProgress progress; // use this to show some progress when the sliding window qualities are calculated for each model 54 41 55 public SlidingWindowBestSolutionsCollectionHeatMapView() { 42 56 InitializeComponent(); 43 44 qualityMeasure = (int)QualityMeasures.PEARSON;57 progress = new Progress(); 58 MainFormManager.GetMainForm<MainForm.WindowsForms.MainForm>().AddOperationProgressToView(this, progress); 45 59 } 46 47 enum QualityMeasures { PEARSON, MSE };48 49 private int qualityMeasure;50 60 51 61 protected override void DeregisterContentEvents() { 52 62 // TODO: Deregister your event handlers here 63 Content.QualitiesCalculationCompleted -= bestSolutionsCollectionQualitiesCalculated; 64 Content.QualitiesCalculationProgress -= bestSolutionCollectionQualitiesCalculationProgress; 65 Content.QualitiesUpdated -= bestSolutionCollectionQualitiesUpdated; 53 66 base.DeregisterContentEvents(); 54 67 } … … 57 70 base.RegisterContentEvents(); 58 71 // TODO: Register your event handlers here 72 Content.QualitiesCalculationCompleted += bestSolutionsCollectionQualitiesCalculated; 73 Content.QualitiesCalculationProgress += bestSolutionCollectionQualitiesCalculationProgress; 74 Content.QualitiesUpdated += bestSolutionCollectionQualitiesUpdated; 59 75 } 60 76 77 private void bestSolutionsCollectionQualitiesCalculated(object sender, RunWorkerCompletedEventArgs e) { 78 if (e.Cancelled || e.Error != null) { 79 progress.Cancel(); 80 return; 81 } 82 SetHeatmapContent(Content.SlidingWindowQualities); 83 progress.Finish(); 84 } 85 86 private void bestSolutionCollectionQualitiesUpdated(object sender, EventArgs e) { 87 SetHeatmapContent(Content.SlidingWindowQualities); 88 } 89 90 private void SetHeatmapContent(double[,] values) { 91 double min = 0, max = 0; 92 foreach (var q in values) { 93 if (min > q) min = q; 94 if (max < q) max = q; 95 } 96 int rows = values.GetLength(0); 97 int cols = values.GetLength(1); 98 var flipped = new double[rows, cols]; 99 for (int i = 0; i < rows; ++i) { 100 for (int j = 0; j < cols; ++j) { 101 flipped[i, j] = values[rows - i - 1, j]; 102 } 103 } 104 heatMapView.Content = new HeatMap(flipped, "Best Sliding Window Solutions", min, max); 105 } 106 107 private void bestSolutionCollectionQualitiesCalculationProgress(object sender, ProgressChangedEventArgs e) { 108 progress.ProgressValue = e.ProgressPercentage / 100.0; 109 } 110 111 protected override void SetEnabledStateOfControls() { 112 base.SetEnabledStateOfControls(); 113 // TODO: Enable or disable controls based on whether the content is null or the view is set readonly 114 } 115 116 #region Event Handlers (child controls) 61 117 public void heatMapView_cellDoubleClick(object sender, DataGridViewCellEventArgs e) { 62 118 var dataGridView = (DataGridView)sender; 63 119 var cell = dataGridView.SelectedCells[0]; 64 var bestSolutions = Content. BestSolutions.Values.ToList();120 var bestSolutions = Content.SlidingWindowBestSolutions.Values.ToList(); 65 121 var tree = bestSolutions[cell.RowIndex]; 66 122 var model = Content.CreateModel(tree, Content.Interpreter); … … 74 130 } 75 131 76 #region Event Handlers (Content)77 // TODO: Put event handlers of the content here78 #endregion79 80 protected override void OnContentChanged() {81 base.OnContentChanged();82 if (Content == null) {83 // TODO: Add code when content has been changed and is null84 } else {85 // TODO: Add code when content has been changed and is not null86 UpdateQualitiesMap();87 }88 }89 90 protected override void SetEnabledStateOfControls() {91 base.SetEnabledStateOfControls();92 // TODO: Enable or disable controls based on whether the content is null or the view is set readonly93 }94 95 #region Event Handlers (child controls)96 // TODO: Put event handlers of child controls here.97 #endregion98 99 132 private void comboBox1_SelectedIndexChanged(object sender, System.EventArgs e) { 100 133 var combobox = (ComboBox)sender; 101 134 switch ((string)combobox.SelectedItem) { 102 135 case "Pearson R2": { 103 qualityMeasure = (int)QualityMeasures.PEARSON;136 Content.QualityMeasure = SlidingWindowBestSolutionsCollection.QualityMeasures.PEARSON; 104 137 break; 105 138 } 106 139 case "Mean Squared Error": { 107 qualityMeasure = (int)QualityMeasures.MSE;140 Content.QualityMeasure = SlidingWindowBestSolutionsCollection.QualityMeasures.MSE; 108 141 break; 109 142 } 110 143 } 111 UpdateQualitiesMap();112 144 } 113 114 private void UpdateQualitiesMap() { 115 var bestSolutions = Content.BestSolutions.Values.ToList(); 116 var swPositions = Content.BestSolutions.Keys.ToList(); 117 118 var nRows = bestSolutions.Count; 119 var nCols = swPositions.Count + 1; 120 var qualitiesMap = new double[nRows, nCols]; 121 double min = 0, max = 0; 122 123 for (int i = 0; i < nCols - 1; ++i) { 124 var pos = swPositions[i]; 125 var rows = Enumerable.Range(pos.Item1, pos.Item2 - pos.Item1).ToList(); 126 127 for (int j = nRows - 1; j >= 0; --j) { 128 var tree = bestSolutions[j]; 129 var q = CalculateQuality(tree, rows); 130 if (min > q) min = q; 131 if (max < q) max = q; 132 qualitiesMap[j, i] = q; 133 } 134 } 135 // deal separately with the last column which represents the whole training partition interval 136 for (int j = nRows - 1; j >= 0; --j) { 137 var tree = bestSolutions[j]; 138 var q = CalculateQuality(tree, Content.ProblemData.TrainingIndices); 139 if (min > q) min = q; 140 if (max < q) max = q; 141 qualitiesMap[j, nCols - 1] = q; 142 } 143 144 heatMapView.Content = new HeatMap(qualitiesMap); 145 heatMapView.Content.Minimum = min; 146 heatMapView.Content.Maximum = max; 147 } 148 149 private string GetTargetVariable(IDataAnalysisProblemData problemData) { 150 var regressionProblemData = problemData as IRegressionProblemData; 151 var classificationProblemData = problemData as IClassificationProblemData; 152 if (regressionProblemData != null) return regressionProblemData.TargetVariable; 153 if (classificationProblemData != null) return classificationProblemData.TargetVariable; 154 throw new NotSupportedException(); 155 } 156 157 private double CalculateQuality(ISymbolicExpressionTree tree, IEnumerable<int> rows) { 158 var estimatedValues = Content.Interpreter.GetSymbolicExpressionTreeValues(tree, Content.ProblemData.Dataset, rows); 159 var originalValues = Content.ProblemData.Dataset.GetDoubleValues(GetTargetVariable(Content.ProblemData), rows); 160 double quality = 0; 161 var errorState = new OnlineCalculatorError(); 162 switch ((QualityMeasures)qualityMeasure) { 163 case QualityMeasures.PEARSON: 164 quality = OnlinePearsonsRSquaredCalculator.Calculate(estimatedValues, originalValues, out errorState); 165 break; 166 case QualityMeasures.MSE: 167 quality = OnlineMeanSquaredErrorCalculator.Calculate(estimatedValues, originalValues, out errorState); 168 break; 169 } 170 return errorState == OnlineCalculatorError.None ? quality : double.NaN; 171 } 145 #endregion 172 146 } 173 147 } -
branches/Sliding Window GP/HeuristicLab.Problems.DataAnalysis.Symbolic.Views/3.4/SlidingWindowBestSolutionsCollectionView.cs
r10413 r10720 22 22 using System; 23 23 using System.Collections.Generic; 24 using System.ComponentModel; 24 25 using System.Linq; 25 26 using System.Windows.Forms; 26 27 using HeuristicLab.Core.Views; 27 28 using HeuristicLab.Data; 28 using HeuristicLab.Encodings.SymbolicExpressionTreeEncoding;29 29 using HeuristicLab.MainForm; 30 30 using HeuristicLab.Optimization; … … 39 39 set { base.Content = value; } 40 40 } 41 public SlidingWindowBestSolutionsCollectionView() {42 InitializeComponent();43 41 44 qualityMeasure = (int)QualityMeasures.PEARSON; 42 protected override void OnContentChanged() { 43 base.OnContentChanged(); 44 if (Content != null) { 45 if (Content.SlidingWindowQualities != null) { 46 SetMatrixContent(Content.SlidingWindowQualities); 47 } else if (!Content.QualitiesCalculationInProgress) { 48 progress.Start("Calculating best solution qualities..."); 49 Content.CalculateQualities(); 50 } 51 } 45 52 } 46 53 47 enum QualityMeasures { PEARSON, MSE }; 48 49 private int qualityMeasure; 54 private readonly Progress progress; 50 55 51 56 protected override void DeregisterContentEvents() { 52 57 // TODO: Deregister your event handlers here 53 58 enhancedStringConvertibleMatrixView.DataGridView.CellDoubleClick -= enhancedStringConvertibleMatrixView_cellDoubleClick; 59 Content.QualitiesCalculationCompleted -= bestSolutionsCollectionQualitiesCalculated; 60 Content.QualitiesCalculationProgress -= bestSolutionCollectionQualitiesCalculationProgress; 61 Content.QualitiesUpdated -= bestSolutionCollectionQualitiesUpdated; 54 62 base.DeregisterContentEvents(); 55 63 } … … 57 65 protected override void RegisterContentEvents() { 58 66 base.RegisterContentEvents(); 67 // TODO: Register your event handlers here 59 68 enhancedStringConvertibleMatrixView.DataGridView.CellDoubleClick += enhancedStringConvertibleMatrixView_cellDoubleClick; 60 // TODO: Register your event handlers here 69 Content.QualitiesCalculationCompleted += bestSolutionsCollectionQualitiesCalculated; 70 Content.QualitiesCalculationProgress += bestSolutionCollectionQualitiesCalculationProgress; 71 Content.QualitiesUpdated += bestSolutionCollectionQualitiesUpdated; 72 } 73 74 public SlidingWindowBestSolutionsCollectionView() { 75 InitializeComponent(); 76 progress = new Progress(); 77 MainFormManager.GetMainForm<MainForm.WindowsForms.MainForm>().AddOperationProgressToView(this, progress); 78 } 79 80 #region Event Handlers (Content) 81 private void bestSolutionsCollectionQualitiesCalculated(object sender, RunWorkerCompletedEventArgs e) { 82 if (e.Cancelled || e.Error != null) { 83 progress.Cancel(); 84 return; 85 } 86 87 SetMatrixContent(Content.SlidingWindowQualities); 88 progress.Finish(); 89 } 90 91 private void SetMatrixContent(double[,] values) { 92 var qualitiesMap = new DoubleMatrix(values); // add an extra columns for the training data 93 qualitiesMap.ColumnNames = Enumerable.Range(0, qualitiesMap.Columns - 1).Select(x => Content.SlidingWindowRanges[x].Start + " - " + Content.SlidingWindowRanges[x].End).Concat(new List<string> { "Training" }); 94 qualitiesMap.RowNames = Enumerable.Range(1, qualitiesMap.Rows).Select(x => "M" + x); 95 96 double min = 0, max = 0; 97 foreach (var q in qualitiesMap) { 98 if (min > q) min = q; 99 if (max < q) max = q; 100 } 101 102 enhancedStringConvertibleMatrixView.Minimum = min; 103 enhancedStringConvertibleMatrixView.Maximum = max; 104 enhancedStringConvertibleMatrixView.Content = qualitiesMap; 105 } 106 107 private void bestSolutionCollectionQualitiesCalculationProgress(object sender, ProgressChangedEventArgs e) { 108 progress.ProgressValue = e.ProgressPercentage / 100.0; 109 } 110 111 private void bestSolutionCollectionQualitiesUpdated(object sender, EventArgs e) { 112 SetMatrixContent(Content.SlidingWindowQualities); 113 } 114 #endregion 115 116 protected override void SetEnabledStateOfControls() { 117 base.SetEnabledStateOfControls(); 118 // TODO: Enable or disable controls based on whether the content is null or the view is set readonly 119 } 120 121 #region Event Handlers (child controls) 122 private void comboBox1_SelectedIndexChanged(object sender, System.EventArgs e) { 123 var combobox = (ComboBox)sender; 124 switch ((string)combobox.SelectedItem) { 125 case "Pearson R2": { 126 Content.QualityMeasure = SlidingWindowBestSolutionsCollection.QualityMeasures.PEARSON; 127 break; 128 } 129 case "Mean Squared Error": { 130 Content.QualityMeasure = SlidingWindowBestSolutionsCollection.QualityMeasures.MSE; 131 break; 132 } 133 } 61 134 } 62 135 … … 64 137 var dataGridView = (DataGridView)sender; 65 138 var cell = dataGridView.SelectedCells[0]; 66 var bestSolutions = Content. BestSolutions.Values.ToList();139 var bestSolutions = Content.SlidingWindowBestSolutions.Values.ToList(); 67 140 var tree = bestSolutions[cell.RowIndex]; 68 141 var model = Content.CreateModel(tree, Content.Interpreter); … … 75 148 } 76 149 } 77 78 #region Event Handlers (Content)79 // TODO: Put event handlers of the content here80 150 #endregion 81 82 protected override void OnContentChanged() {83 base.OnContentChanged();84 if (Content == null) {85 // TODO: Add code when content has been changed and is null86 } else {87 // TODO: Add code when content has been changed and is not null88 UpdateQualitiesMap();89 }90 }91 92 protected override void SetEnabledStateOfControls() {93 base.SetEnabledStateOfControls();94 // TODO: Enable or disable controls based on whether the content is null or the view is set readonly95 }96 97 #region Event Handlers (child controls)98 // TODO: Put event handlers of child controls here.99 #endregion100 101 private void comboBox1_SelectedIndexChanged(object sender, System.EventArgs e) {102 var combobox = (ComboBox)sender;103 switch ((string)combobox.SelectedItem) {104 case "Pearson R2": {105 qualityMeasure = (int)QualityMeasures.PEARSON;106 break;107 }108 case "Mean Squared Error": {109 qualityMeasure = (int)QualityMeasures.MSE;110 break;111 }112 }113 UpdateQualitiesMap();114 }115 116 private void UpdateQualitiesMap() {117 var bestSolutions = Content.BestSolutions.Values.ToList();118 var swPositions = Content.BestSolutions.Keys.ToList();119 var qualitiesMap = new DoubleMatrix(bestSolutions.Count, swPositions.Count + 1);120 qualitiesMap.ColumnNames = swPositions.Select(x => x.Item1 + "-" + x.Item2).Concat(new List<string> { "Training" });121 qualitiesMap.RowNames = Enumerable.Range(1, bestSolutions.Count).Select(x => "M" + x);122 double min = 0, max = 0;123 124 for (int i = 0; i < qualitiesMap.Columns - 1; ++i) {125 var pos = swPositions[i];126 var rows = Enumerable.Range(pos.Item1, pos.Item2 - pos.Item1).ToList();127 128 for (int j = 0; j < qualitiesMap.Rows; ++j) {129 var tree = bestSolutions[j];130 var q = CalculateQuality(tree, rows);131 if (min > q) min = q;132 if (max < q) max = q;133 qualitiesMap[j, i] = q;134 }135 }136 // deal separately with the last column which represents the whole training partition interval137 for (int j = 0; j < qualitiesMap.Rows; ++j) {138 var tree = bestSolutions[j];139 var q = CalculateQuality(tree, Content.ProblemData.TrainingIndices);140 if (min > q) min = q;141 if (max < q) max = q;142 qualitiesMap[j, qualitiesMap.Columns - 1] = q;143 }144 145 enhancedStringConvertibleMatrixView.Minimum = min;146 enhancedStringConvertibleMatrixView.Maximum = max;147 enhancedStringConvertibleMatrixView.Content = qualitiesMap;148 }149 150 private string GetTargetVariable(IDataAnalysisProblemData problemData) {151 var regressionProblemData = problemData as IRegressionProblemData;152 var classificationProblemData = problemData as IClassificationProblemData;153 if (regressionProblemData != null) return regressionProblemData.TargetVariable;154 if (classificationProblemData != null) return classificationProblemData.TargetVariable;155 throw new NotSupportedException();156 }157 158 private double CalculateQuality(ISymbolicExpressionTree tree, IEnumerable<int> rows) {159 var estimatedValues = Content.Interpreter.GetSymbolicExpressionTreeValues(tree, Content.ProblemData.Dataset, rows);160 var originalValues = Content.ProblemData.Dataset.GetDoubleValues(GetTargetVariable(Content.ProblemData), rows);161 double quality = 0;162 var errorState = new OnlineCalculatorError();163 switch ((QualityMeasures)qualityMeasure) {164 case QualityMeasures.PEARSON:165 quality = OnlinePearsonsRSquaredCalculator.Calculate(estimatedValues, originalValues, out errorState);166 break;167 case QualityMeasures.MSE:168 quality = OnlineMeanSquaredErrorCalculator.Calculate(estimatedValues, originalValues, out errorState);169 break;170 }171 return errorState == OnlineCalculatorError.None ? quality : double.NaN;172 }173 151 } 174 152 } -
branches/Sliding Window GP/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SlidingWindow/SlidingWindowAnalyzer.cs
r10413 r10720 31 31 using HeuristicLab.Persistence.Default.CompositeSerializers.Storable; 32 32 33 33 34 namespace HeuristicLab.Problems.DataAnalysis.Symbolic { 34 35 [StorableClass] … … 45 46 private const string TerminateSlidingWindowParameterName = "TerminateSlidingWindow"; 46 47 private const string InterpreterParameterName = "SymbolicExpressionTreeInterpreter"; 48 protected const string BestSlidingWindowSolutionsResultName = "Best Sliding Window Solutions"; 47 49 48 50 #region parameter properties … … 179 181 180 182 private void SaveBestSolution() { 181 var bestSolutionsCollection = (SlidingWindowBestSolutionsCollection)ResultCollection[ "Best Solutions"].Value;183 var bestSolutionsCollection = (SlidingWindowBestSolutionsCollection)ResultCollection[BestSlidingWindowSolutionsResultName].Value; 182 184 183 if (bestSolutionsCollection.ProblemData == null) 184 bestSolutionsCollection.ProblemData = ProblemData; 185 186 if (bestSolutionsCollection.Interpreter == null) 187 bestSolutionsCollection.Interpreter = Interpreter; 185 bestSolutionsCollection.ProblemData = ProblemData; 186 bestSolutionsCollection.Interpreter = Interpreter; 187 bestSolutionsCollection.ApplyLinearScaling = ApplyLinearScalingParameter.ActualValue.Value; 188 188 189 189 var fitnessPartition = FitnessCalculationPartitionParameter.ActualValue; 190 190 var best = FindBestIndividual(); 191 var range = new Tuple<int, int>(fitnessPartition.Start, fitnessPartition.End);191 var range = new SlidingWindowRange(fitnessPartition.Start, fitnessPartition.End); 192 192 193 193 bestSolutionsCollection[range] = best; -
branches/Sliding Window GP/HeuristicLab.Problems.DataAnalysis.Symbolic/3.4/SlidingWindow/SlidingWindowBestSolutionsCollection.cs
r10413 r10720 20 20 #endregion 21 21 22 using System; 22 23 using System.Collections.Generic; 24 using System.ComponentModel; 25 using System.Linq; 23 26 using HeuristicLab.Common; 24 27 using HeuristicLab.Core; … … 26 29 using HeuristicLab.Persistence.Default.CompositeSerializers.Storable; 27 30 28 using SlidingWindowRange = System.Tuple<int, int>;29 30 31 namespace HeuristicLab.Problems.DataAnalysis.Symbolic { 31 32 [StorableClass] … … 33 34 public abstract class SlidingWindowBestSolutionsCollection : Item { 34 35 [Storable] 35 private Dictionary<SlidingWindowRange, ISymbolicExpressionTree> bestSolutions; 36 public Dictionary<SlidingWindowRange, ISymbolicExpressionTree> BestSolutions { 37 get { return bestSolutions; } 38 set { bestSolutions = value; } 36 private List<SlidingWindowRange> slidingWindowRanges; 37 public List<SlidingWindowRange> SlidingWindowRanges { 38 get { return slidingWindowRanges; } 39 private set { slidingWindowRanges = value; } 40 } 41 42 [Storable(AllowOneWay = true, Name = "bestSolutions")] 43 private Dictionary<Tuple<int, int>, ISymbolicExpressionTree> StorableBestSolutions { 44 set { 45 var bestSolutions = value; 46 var ranges = bestSolutions.Keys.OrderBy(x => x.Item1).ToList(); 47 slidingWindowRanges = ranges.Select(x => new SlidingWindowRange(x.Item1, x.Item2)).ToList(); 48 slidingWindowBestSolutions = new Dictionary<SlidingWindowRange, ISymbolicExpressionTree>(); 49 for (int i = 0; i < slidingWindowRanges.Count; ++i) { 50 slidingWindowBestSolutions.Add(slidingWindowRanges[i], bestSolutions[ranges[i]]); 51 } 52 } 53 } 54 55 [Storable] 56 private Dictionary<SlidingWindowRange, ISymbolicExpressionTree> slidingWindowBestSolutions; 57 public Dictionary<SlidingWindowRange, ISymbolicExpressionTree> SlidingWindowBestSolutions { 58 get { return slidingWindowBestSolutions; } 59 set { slidingWindowBestSolutions = value; } 39 60 } 40 61 … … 52 73 set { interpreter = value; } 53 74 } 75 76 [Storable] 77 private bool applyLinearScaling; 78 public bool ApplyLinearScaling { 79 get { return applyLinearScaling; } 80 set { applyLinearScaling = value; } 81 } 82 54 83 [StorableHook(HookType.AfterDeserialization)] 55 84 private void AfterDeserialization() { 85 if (bw == null) { 86 bw = new BackgroundWorker(); 87 bw.WorkerSupportsCancellation = true; 88 bw.WorkerReportsProgress = true; 89 bw.DoWork += CalculateQualities; 90 } 91 } 92 93 public double[,] SlidingWindowQualities { get; set; } 94 95 private BackgroundWorker bw; 96 97 public enum QualityMeasures { PEARSON, MSE }; 98 99 private QualityMeasures qualityMeasure; 100 public QualityMeasures QualityMeasure { 101 get { return qualityMeasure; } 102 set { 103 if (qualityMeasure != value) { 104 qualityMeasure = value; 105 CalculateQualities(); 106 } 107 } 108 } 109 110 public bool QualitiesCalculationInProgress { 111 get { return bw.IsBusy; } 112 } 113 114 public event ProgressChangedEventHandler QualitiesCalculationProgress { 115 add { bw.ProgressChanged += value; } 116 remove { bw.ProgressChanged -= value; } 117 } 118 119 public event RunWorkerCompletedEventHandler QualitiesCalculationCompleted { 120 add { bw.RunWorkerCompleted += value; } 121 remove { bw.RunWorkerCompleted -= value; } 122 } 123 124 public event EventHandler QualitiesUpdated; 125 private void OnQualitiesUpdated(object sender, EventArgs e) { 126 var updated = QualitiesUpdated; 127 if (updated != null) { updated(sender, e); } 56 128 } 57 129 … … 60 132 protected SlidingWindowBestSolutionsCollection(SlidingWindowBestSolutionsCollection original, Cloner cloner) 61 133 : base(original, cloner) { 62 this. bestSolutions = original.bestSolutions;134 this.slidingWindowBestSolutions = original.slidingWindowBestSolutions; 63 135 this.problemData = original.problemData; 64 136 this.interpreter = original.interpreter; 137 this.applyLinearScaling = original.ApplyLinearScaling; 65 138 } 66 139 protected SlidingWindowBestSolutionsCollection() { 67 bestSolutions = new Dictionary<SlidingWindowRange, ISymbolicExpressionTree>(); 140 slidingWindowBestSolutions = new Dictionary<SlidingWindowRange, ISymbolicExpressionTree>(); 141 slidingWindowRanges = new List<SlidingWindowRange>(); 142 qualityMeasure = QualityMeasures.PEARSON; 143 144 bw = new BackgroundWorker(); 145 bw.WorkerSupportsCancellation = true; 146 bw.WorkerReportsProgress = true; 147 148 bw.DoWork += CalculateQualities; 68 149 } 69 150 70 151 public bool ContainsKey(SlidingWindowRange key) { 71 return bestSolutions.ContainsKey(key);152 return slidingWindowBestSolutions.ContainsKey(key); 72 153 } 73 154 74 155 public ISymbolicExpressionTree this[SlidingWindowRange key] { 75 156 get { 76 return bestSolutions[key];157 return slidingWindowBestSolutions[key]; 77 158 } 78 159 set { 79 if (bestSolutions.ContainsKey(key)) 80 bestSolutions[key] = value; 81 else 82 bestSolutions.Add(key, value); 160 AddSolution(key, value); // this should be fast so there's no need for a background worker 161 OnQualitiesUpdated(this, EventArgs.Empty); 83 162 } 84 163 } 85 164 86 165 public void Add(SlidingWindowRange range, ISymbolicExpressionTree solution) { 87 bestSolutions.Add(range, solution); 166 if (!slidingWindowBestSolutions.ContainsKey(range)) { 167 slidingWindowBestSolutions.Add(range, solution); 168 slidingWindowRanges.Add(range); 169 } else { 170 slidingWindowBestSolutions[range] = solution; 171 } 88 172 } 89 173 90 174 public void Clear() { 91 if (bestSolutions != null) bestSolutions.Clear(); 175 if (slidingWindowBestSolutions != null) slidingWindowBestSolutions.Clear(); 176 if (slidingWindowRanges != null) slidingWindowRanges.Clear(); 92 177 } 93 178 … … 96 181 97 182 public abstract ISymbolicDataAnalysisSolution CreateSolution(ISymbolicDataAnalysisModel model, IDataAnalysisProblemData problemData); 183 184 private void AddSolution(SlidingWindowRange range, ISymbolicExpressionTree solution) { 185 // add a solution and update the qualities matrix 186 Add(range, solution); 187 188 var solutions = slidingWindowRanges.Select(x => slidingWindowBestSolutions[x]).ToList(); 189 190 var nRows = solutions.Count; 191 var nCols = nRows + 1; // an extra column corresponding to the whole trainig partition 192 193 var trainingIndices = problemData.TrainingIndices.ToList(); 194 var matrix = new double[nRows, nCols]; 195 List<int> rows; 196 // copy old qualities into the new matrix 197 for (int i = 0; i < nRows - 1; ++i) { 198 for (int j = 0; j < nCols - 1; ++j) { 199 matrix[i, j] = SlidingWindowQualities[i, j]; 200 } 201 } 202 // copy qualities of new solution into the new matrix 203 for (int i = 0; i < nCols; ++i) { 204 rows = i == nCols - 1 ? trainingIndices : Enumerable.Range(slidingWindowRanges[i].Start, slidingWindowRanges[i].Size).ToList(); 205 matrix[nRows - 1, i] = CalculateQuality(solution, rows); 206 } 207 // shift old training qualities one column to the right 208 rows = Enumerable.Range(range.Start, range.Size).ToList(); 209 for (int i = 0; i < nRows; ++i) { 210 matrix[i, nCols - 1] = matrix[i, nCols - 2]; 211 matrix[i, nCols - 2] = CalculateQuality(solutions[i], rows); 212 } 213 // replace old matrix with new matrix 214 SlidingWindowQualities = matrix; 215 } 216 217 private void CalculateQualities(object sender, DoWorkEventArgs e) { 218 var worker = sender as BackgroundWorker; 219 if (worker == null) return; 220 if (worker.CancellationPending) { 221 e.Cancel = true; 222 return; 223 } 224 225 var ranges = SlidingWindowRanges; 226 var solutions = ranges.Select(x => SlidingWindowBestSolutions[x]).ToList(); 227 228 int rows = solutions.Count; 229 int columns = ranges.Count + 1; 230 231 SlidingWindowQualities = new double[rows, columns]; 232 233 for (int i = 0; i < rows; ++i) { 234 if (worker.CancellationPending) { 235 e.Cancel = true; 236 return; 237 } 238 239 var solution = solutions[i]; 240 for (int j = 0; j < columns; ++j) { 241 var range = (j == columns - 1) ? ProblemData.TrainingIndices : Enumerable.Range(ranges[j].Start, ranges[j].Size); 242 var q = CalculateQuality(solution, range); 243 244 SlidingWindowQualities[i, j] = q; 245 } 246 247 worker.ReportProgress((int)Math.Round(i * 100.0 / rows)); 248 } 249 } 250 251 public void CalculateQualities() { 252 bw.RunWorkerAsync(); 253 } 254 255 private string GetTargetVariable(IDataAnalysisProblemData problemData) { 256 var regressionProblemData = problemData as IRegressionProblemData; 257 var classificationProblemData = problemData as IClassificationProblemData; 258 if (regressionProblemData != null) return regressionProblemData.TargetVariable; 259 if (classificationProblemData != null) return classificationProblemData.TargetVariable; 260 throw new NotSupportedException(); 261 } 262 263 private double CalculateQuality(ISymbolicExpressionTree tree, IEnumerable<int> rows) { 264 var estimatedValues = Interpreter.GetSymbolicExpressionTreeValues(tree, ProblemData.Dataset, rows); 265 var originalValues = ProblemData.Dataset.GetDoubleValues(GetTargetVariable(ProblemData), rows); 266 double quality = 0; 267 var errorState = new OnlineCalculatorError(); 268 switch (QualityMeasure) { 269 case QualityMeasures.PEARSON: 270 quality = OnlinePearsonsRSquaredCalculator.Calculate(estimatedValues, originalValues, out errorState); 271 break; 272 case QualityMeasures.MSE: 273 quality = OnlineMeanSquaredErrorCalculator.Calculate(estimatedValues, originalValues, out errorState); 274 break; 275 } 276 return errorState == OnlineCalculatorError.None ? quality : double.NaN; 277 } 278 } 279 280 public class SlidingWindowRange : IEquatable<SlidingWindowRange> { 281 private readonly Tuple<int, int> tuple; 282 283 public int Start { get { return tuple.Item1; } } 284 285 public int End { get { return tuple.Item2; } } 286 287 public SlidingWindowRange(int start, int end) { 288 if (start > end) throw new ArgumentException("SlidingWindowRange: Start cannot be greater than End."); 289 tuple = new Tuple<int, int>(start, end); 290 } 291 292 public bool Equals(SlidingWindowRange other) { 293 return tuple.Equals(other.tuple); 294 } 295 296 public override int GetHashCode() { 297 return tuple.GetHashCode(); 298 } 299 300 public int Size { 301 get { return End - Start; } 302 } 98 303 } 99 304 }
Note: See TracChangeset
for help on using the changeset viewer.