Changeset 15884 for branches/2906_Transformations
- Timestamp:
- 04/04/18 17:18:02 (7 years ago)
- Location:
- branches/2906_Transformations
- Files:
-
- 18 edited
Legend:
- Unmodified
- Added
- Removed
-
branches/2906_Transformations/HeuristicLab.DataPreprocessing.Views/3.4/PreprocessingCheckedVariablesView.cs
r15583 r15884 42 42 protected PreprocessingCheckedVariablesView() { 43 43 InitializeComponent(); 44 45 // TODO: fix auto-size of columns 46 //for (int i = 0; i < variablesListView.Columns.Count; i++) { 47 // variablesListView.Columns[i].Width = -1; 48 // variablesListView.Columns[i].AutoResize(ColumnHeaderAutoResizeStyle.ColumnContent); 49 //} 44 50 } 45 51 -
branches/2906_Transformations/HeuristicLab.DataPreprocessing/3.4/ProblemDataCreator.cs
r15880 r15884 23 23 using System.Collections.Generic; 24 24 using System.Linq; 25 using HeuristicLab.Common;26 25 using HeuristicLab.Problems.DataAnalysis; 27 26 … … 46 45 47 46 IDataAnalysisProblemData problemData; 48 49 47 if (oldProblemData is TimeSeriesPrognosisProblemData) { 50 48 problemData = CreateTimeSeriesPrognosisData((TimeSeriesPrognosisProblemData)oldProblemData); … … 59 57 } 60 58 61 SetTrainingAndTestPartition(problemData); 62 SetAllowedInputVariables(problemData, oldProblemData.AllowedInputVariables); 63 // set the input variables to the correct checked state 64 //var inputVariables = oldProblemData.InputVariables.ToDictionary(x => x.Value, x => x); 65 //foreach (var variable in problemData.InputVariables) { 66 // bool isChecked = inputVariables.ContainsKey(variable.Value) && oldProblemData.InputVariables.ItemChecked(inputVariables[variable.Value]); 67 // problemData.InputVariables.SetItemCheckedState(variable, isChecked); 68 //} 59 SetTrainingAndTestPartition(problemData, context.Data); 60 SetAllowedInputVariables(problemData, oldProblemData); 69 61 70 62 return problemData; … … 75 67 if (!context.Data.VariableNames.Contains(targetVariable)) 76 68 targetVariable = context.Data.VariableNames.First(); 77 var inputVariables = GetDoubleInputVariables(targetVariable); 78 var newProblemData = new TimeSeriesPrognosisProblemData(ExportedDataset, inputVariables, targetVariable, CreateDataAnalysisTransformation()) { 69 var newProblemData = new TimeSeriesPrognosisProblemData(ExportedDataset, Enumerable.Empty<string>(), targetVariable, CreateDataAnalysisTransformation()) { 79 70 TrainingHorizon = oldProblemData.TrainingHorizon, 80 71 TestHorizon = oldProblemData.TestHorizon … … 84 75 85 76 private IDataAnalysisProblemData CreateRegressionData(RegressionProblemData oldProblemData) { 86 // TODO: transformations (additional inputs, target changed) 87 var targetVariable = RegressionTransformationModel.GetTransformedTragetVariable(oldProblemData.TargetVariable, CreateDataAnalysisTransformation()); 77 var targetVariable = DataAnalysisTransformation.GetLastTransitiveVariable(oldProblemData.TargetVariable, CreateDataAnalysisTransformation()); 88 78 if (!context.Data.VariableNames.Contains(targetVariable)) 89 79 targetVariable = context.Data.VariableNames.First(); 90 var inputVariables = GetDoubleInputVariables(targetVariable); 91 var newProblemData = new RegressionProblemData(ExportedDataset, inputVariables, targetVariable, CreateDataAnalysisTransformation()); 80 var newProblemData = new RegressionProblemData(ExportedDataset, Enumerable.Empty<string>(), targetVariable, CreateDataAnalysisTransformation()); 92 81 return newProblemData; 93 82 } … … 97 86 if (!context.Data.VariableNames.Contains(targetVariable)) 98 87 targetVariable = context.Data.VariableNames.First(); 99 var inputVariables = GetDoubleInputVariables(targetVariable); 100 var newProblemData = new ClassificationProblemData(ExportedDataset, inputVariables, targetVariable, CreateDataAnalysisTransformation()) { 88 var newProblemData = new ClassificationProblemData(ExportedDataset, Enumerable.Empty<string>(), targetVariable, CreateDataAnalysisTransformation()) { 101 89 PositiveClass = oldProblemData.PositiveClass 102 90 }; … … 105 93 106 94 private IDataAnalysisProblemData CreateClusteringData(ClusteringProblemData oldProblemData) { 107 return new ClusteringProblemData(ExportedDataset, GetDoubleInputVariables(String.Empty), CreateDataAnalysisTransformation());95 return new ClusteringProblemData(ExportedDataset, Enumerable.Empty<string>(), CreateDataAnalysisTransformation()); 108 96 } 109 97 110 private void SetTrainingAndTestPartition(IDataAnalysisProblemData problemData) { 111 var ppData = context.Data; 112 98 private static void SetTrainingAndTestPartition(IDataAnalysisProblemData problemData, IPreprocessingData ppData) { 113 99 problemData.TrainingPartition.Start = ppData.TrainingPartition.Start; 114 100 problemData.TrainingPartition.End = ppData.TrainingPartition.End; … … 117 103 } 118 104 119 void SetAllowedInputVariables(IDataAnalysisProblemData problemData, IEnumerable<string> oldInputVariables) {120 var inputs = DataAnalysisTransformationModel.ExtendInputVariables(oldInputVariables, problemData.Transformations);121 105 private static void SetAllowedInputVariables(IDataAnalysisProblemData problemData, IDataAnalysisProblemData oldProblemData) { 106 // original inputs + extended(transitive) inputs 107 var inputs = DataAnalysisTransformation.ExtendVariables(oldProblemData.AllowedInputVariables, problemData.Transformations).ToList(); 122 108 foreach (var input in problemData.InputVariables) { 123 109 problemData.InputVariables.SetItemCheckedState(input, inputs.Contains(input.Value)); 124 110 } 125 }126 111 127 private IEnumerable<string> GetDoubleInputVariables(string targetVariable) { 128 var variableNames = new List<string>(); 129 for (int i = 0; i < context.Data.Columns; ++i) { 130 var variableName = context.Data.GetVariableName(i); 131 if (context.Data.VariableHasType<double>(i) 132 && variableName != targetVariable 133 && IsNotConstantInputVariable(context.Data.GetValues<double>(i))) { 134 135 variableNames.Add(variableName); 136 } 112 // new variables that were not created via transformations 113 var originalAndVirtualVariables = DataAnalysisTransformation.ExtendVariables(oldProblemData.Dataset.VariableNames, problemData.Transformations); 114 var newVariables = problemData.Dataset.VariableNames.Except(originalAndVirtualVariables).ToList(); 115 foreach (var input in problemData.InputVariables) { 116 if (newVariables.Contains(input.Value)) 117 problemData.InputVariables.SetItemCheckedState(input, true); 137 118 } 138 return variableNames;139 }140 141 private bool IsNotConstantInputVariable(IList<double> list) {142 return context.Data.TrainingPartition.End - context.Data.TrainingPartition.Start > 1 || list.Range() > 0;143 119 } 144 120 -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis.Views/3.4/DataAnalysisTransformationModelView.Designer.cs
r15870 r15884 45 45 /// </summary> 46 46 private void InitializeComponent() { 47 this. originalModelTabPage = new System.Windows.Forms.TabPage();47 this.trainedModelTabPage = new System.Windows.Forms.TabPage(); 48 48 this.modelViewHost = new HeuristicLab.MainForm.WindowsForms.ViewHost(); 49 49 this.tabControl = new System.Windows.Forms.TabControl(); … … 52 52 this.targetTransformationsTabPage = new System.Windows.Forms.TabPage(); 53 53 this.targetTransformationsViewHost = new HeuristicLab.MainForm.WindowsForms.ViewHost(); 54 this. originalModelTabPage.SuspendLayout();54 this.trainedModelTabPage.SuspendLayout(); 55 55 this.tabControl.SuspendLayout(); 56 56 this.inputTransformationsTabPage.SuspendLayout(); … … 58 58 this.SuspendLayout(); 59 59 // 60 // originalModelTabPage60 // trainedModelTabPage 61 61 // 62 this. originalModelTabPage.Controls.Add(this.modelViewHost);63 this. originalModelTabPage.Location = new System.Drawing.Point(4, 22);64 this. originalModelTabPage.Name = "originalModelTabPage";65 this. originalModelTabPage.Padding = new System.Windows.Forms.Padding(3);66 this. originalModelTabPage.Size = new System.Drawing.Size(486, 392);67 this. originalModelTabPage.TabIndex = 0;68 this. originalModelTabPage.Text = "OriginalModel";69 this. originalModelTabPage.UseVisualStyleBackColor = true;62 this.trainedModelTabPage.Controls.Add(this.modelViewHost); 63 this.trainedModelTabPage.Location = new System.Drawing.Point(4, 22); 64 this.trainedModelTabPage.Name = "trainedModelTabPage"; 65 this.trainedModelTabPage.Padding = new System.Windows.Forms.Padding(3); 66 this.trainedModelTabPage.Size = new System.Drawing.Size(486, 392); 67 this.trainedModelTabPage.TabIndex = 0; 68 this.trainedModelTabPage.Text = "Trained Model"; 69 this.trainedModelTabPage.UseVisualStyleBackColor = true; 70 70 // 71 71 // modelViewHost … … 88 88 | System.Windows.Forms.AnchorStyles.Left) 89 89 | System.Windows.Forms.AnchorStyles.Right))); 90 this.tabControl.Controls.Add(this. originalModelTabPage);90 this.tabControl.Controls.Add(this.trainedModelTabPage); 91 91 this.tabControl.Controls.Add(this.inputTransformationsTabPage); 92 92 this.tabControl.Controls.Add(this.targetTransformationsTabPage); … … 154 154 this.Name = "DataAnalysisTransformationModelView"; 155 155 this.Size = new System.Drawing.Size(500, 424); 156 this. originalModelTabPage.ResumeLayout(false);156 this.trainedModelTabPage.ResumeLayout(false); 157 157 this.tabControl.ResumeLayout(false); 158 158 this.inputTransformationsTabPage.ResumeLayout(false); … … 164 164 #endregion 165 165 166 private System.Windows.Forms.TabPage originalModelTabPage;166 private System.Windows.Forms.TabPage trainedModelTabPage; 167 167 private MainForm.WindowsForms.ViewHost modelViewHost; 168 168 private System.Windows.Forms.TabControl tabControl; -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis.Views/3.4/DataAnalysisTransformationModelView.cs
r15870 r15884 18 18 * along with HeuristicLab. If not, see <http://www.gnu.org/licenses/>. 19 19 */ 20 #endregion 20 #endregion 21 21 22 22 using HeuristicLab.Core.Views; … … 25 25 namespace HeuristicLab.Problems.DataAnalysis.Views { 26 26 [View("Transformation Model View")] 27 [Content(typeof( IDataAnalysisTransformationModel), true)]27 [Content(typeof(DataAnalysisTransformationModel), true)] 28 28 public partial class DataAnalysisTransformationModelView : ItemView { 29 29 30 public new IDataAnalysisTransformationModel Content {31 get { return ( IDataAnalysisTransformationModel)base.Content; }30 public new DataAnalysisTransformationModel Content { 31 get { return (DataAnalysisTransformationModel)base.Content; } 32 32 set { base.Content = value; } 33 33 } -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis.Views/3.4/Solution Views/DataAnalysisSolutionView.cs
r15870 r15884 40 40 41 41 private const string BacktransformButtonText = "Integrate Transformations"; 42 private const string ReapplyTransformationsButtonText = "Restore OriginalModel";42 private const string ReapplyTransformationsButtonText = "Restore Trained Model"; 43 43 44 44 public DataAnalysisSolutionView() { … … 93 93 94 94 transformButton.Text = Content.Model is IDataAnalysisTransformationModel 95 ? ReapplyTransformationsButtonText : BacktransformButtonText; 95 ? ReapplyTransformationsButtonText 96 : BacktransformButtonText; 96 97 } 97 98 … … 237 238 problemData = param.Value as DataAnalysisProblemData; 238 239 } 240 239 241 if (problemData == null) return; 240 242 … … 258 260 259 261 private void transformButton_Click(object sender, EventArgs e) { 260 var transformedSolution = CreateTransformedSolution(Content);262 var transformedSolution = DataAnalysisTransformation.TransformSolution(Content); 261 263 MainFormManager.MainForm.ShowContent(transformedSolution); 262 264 } 263 264 private static IDataAnalysisSolution CreateTransformedSolution(IDataAnalysisSolution solution) {265 if (solution.Model is IRegressionTransformationModel regressionTransformationModel && !(solution.Model is ITimeSeriesPrognosisTransformationModel)) {266 var originalData = (IRegressionProblemData)((IRegressionSolution)solution).ProblemData.Transform();267 return regressionTransformationModel.OriginalModel.CreateRegressionSolution(originalData);268 } else if (solution.Model is IClassificationTransformationModel classificationTransformationModel) {269 var originalData = (IClassificationProblemData)((IClassificationSolution)solution).ProblemData.Transform();270 return classificationTransformationModel.OriginalModel.CreateClassificationSolution(originalData);271 } else if (solution.Model is IRegressionModel regressionModel && !(solution.Model is ITimeSeriesPrognosisModel)) {272 var transformationModel = new RegressionTransformationModel(regressionModel, solution.ProblemData.Transformations);273 var transformedData = (IRegressionProblemData)((IRegressionSolution)solution).ProblemData.InverseTransform();274 return transformationModel.CreateRegressionSolution(transformedData);275 } else if (solution.Model is IClassificationModel classificationModel) {276 var transformationModel = new ClassificationTransformationModel(classificationModel, solution.ProblemData.Transformations);277 var transformedData = (IClassificationProblemData)((IClassificationSolution)solution).ProblemData.InverseTransform();278 return transformationModel.CreateClassificationSolution(transformedData);279 } else throw new NotSupportedException();280 }281 282 /*if (Content.Model is IDataAnalysisTransformationModel transformationModel) {283 var originalModel = transformationModel.InverseTransform();284 originalModel.CreateSolution();285 } else {286 var originalModel = Content.Model;287 var transformationModel = originalModel.Transform();288 transformationModel.CreateSolution();289 }*/290 291 ////Content.Model.Transform()292 293 //var transformedModel = new DataAnalysisTransformationModel(Content.Model, Content.ProblemData.Transformations);294 //var originalProblemData = (IRegressionProblemData)Content.ProblemData.InverseTransform();295 //var transformedSolution = new TransformedRegressionSolution(transformedModel, originalProblemData);296 //MainFormManager.MainForm.ShowContent(transformedSolution);297 265 } 298 266 } -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Classification/ClassificationTransformationModel.cs
r15870 r15884 35 35 } 36 36 37 38 37 #region Constructor, Cloning & Persistence 39 38 public ClassificationTransformationModel(IClassificationModel originalModel, IEnumerable<IDataAnalysisTransformation> transformations) 40 39 : base(originalModel, transformations) { 41 if ( CalculateTransitiveVariables(new[] { originalModel.TargetVariable }, transformations).Any())40 if (DataAnalysisTransformation.GetTransitiveVariables(new[] { originalModel.TargetVariable }, transformations).Any()) 42 41 throw new NotSupportedException("Classification with a transformed target variable is not allowed"); 43 42 } … … 57 56 58 57 public virtual IEnumerable<double> GetEstimatedClassValues(IDataset dataset, IEnumerable<int> rows) { 59 return OriginalModel.GetEstimatedClassValues(Transform(dataset, InputTransformations), rows); 58 var transformedInput = DataAnalysisTransformation.Transform(dataset, InputTransformations); 59 return OriginalModel.GetEstimatedClassValues(transformedInput, rows); 60 60 } 61 61 -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Clustering/ClusteringTransformationModel.cs
r15870 r15884 53 53 54 54 public IEnumerable<int> GetClusterValues(IDataset dataset, IEnumerable<int> rows) { 55 return OriginalModel.GetClusterValues(Transform(dataset, InputTransformations), rows); 55 var transformedInputs = DataAnalysisTransformation.Transform(dataset, InputTransformations); 56 return OriginalModel.GetClusterValues(transformedInputs, rows); 56 57 } 57 58 } -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/DataAnalysisProblemData.cs
r15879 r15884 241 241 } 242 242 } 243 244 public virtual IDataAnalysisProblemData Transform() {245 var newDataset = DataAnalysisTransformationModel.Transform(Dataset, Transformations);246 247 var extendedInputs = DataAnalysisTransformationModel.ExtendInputVariables(AllowedInputVariables, Transformations);248 var checkedInputs = new CheckedItemList<StringValue>(newDataset.VariableNames.Select(x => new StringValue(x)));249 foreach (var input in checkedInputs) checkedInputs.SetItemCheckedState(input, extendedInputs.Contains(input.Value));250 251 // TODO: Cannot create concrete instance here (maybe derived Create-method?)252 var cloner = new Cloner();253 cloner.RegisterClonedObject(Dataset, newDataset);254 cloner.RegisterClonedObject(InputVariables, checkedInputs.AsReadOnly());255 // TODO: valid values for target are not extended256 257 return cloner.Clone(this);258 }259 260 public virtual IDataAnalysisProblemData InverseTransform() {261 var newDataset = InverseTransform(Dataset, Transformations);262 263 var checkedInputs = new CheckedItemList<StringValue>(newDataset.VariableNames.Select(x => new StringValue(x)));264 foreach (var input in checkedInputs) checkedInputs.SetItemCheckedState(input, AllowedInputVariables.Contains(input.Value));265 266 // TODO: Cannot create concrete instance here (maybe derived Create-method?)267 var cloner = new Cloner();268 cloner.RegisterClonedObject(Dataset, newDataset);269 cloner.RegisterClonedObject(InputVariables, checkedInputs.AsReadOnly());270 // TODO: check valid target values271 272 return cloner.Clone(this);273 }274 275 public static IDataset InverseTransform(IDataset dataset, IEnumerable<IDataAnalysisTransformation> transformations, bool removeVirtualVariables = true) {276 var modifiableDataset = ((Dataset)dataset).ToModifiable();277 278 var transformationsStack = new Stack<IDataAnalysisTransformation>(transformations);279 while (transformationsStack.Any()) {280 var transformation = transformationsStack.Pop();281 var trans = (ITransformation<double>)transformation.Transformation;282 283 var prevTransformations = transformations.Except(transformationsStack);284 bool originalWasChanged = prevTransformations.Any(x => x.TransformedVariable == transformation.OriginalVariable);285 if (originalWasChanged) {286 var transformedData = modifiableDataset.GetDoubleValues(transformation.TransformedVariable);287 288 var originalData = trans.InverseApply(transformedData).ToList();289 modifiableDataset.ReplaceVariable(transformation.OriginalVariable, originalData);290 }291 292 bool transformedVariablePending = transformationsStack.Any(x => x.OriginalVariable == transformation.TransformedVariable || x.TransformedVariable == transformation.TransformedVariable);293 if (removeVirtualVariables && !transformedVariablePending)294 modifiableDataset.RemoveVariable(transformation.TransformedVariable);295 }296 297 return modifiableDataset;298 }299 243 } 300 244 } -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/DataAnalysisTransformation.cs
r15879 r15884 20 20 #endregion 21 21 22 using System; 23 using System.Collections.Generic; 24 using System.Linq; 22 25 using HeuristicLab.Common; 23 26 using HeuristicLab.Core; … … 67 70 68 71 private DataAnalysisTransformation(DataAnalysisTransformation original, Cloner cloner) 69 : base(original, cloner) { 70 } 72 : base(original, cloner) { } 71 73 72 74 public override IDeepCloneable Clone(Cloner cloner) { … … 84 86 return $"{Transformation} ({OriginalVariable} -> {TransformedVariable})"; 85 87 } 88 89 #region Transformation 90 91 #region Variable Extension & Reduction 92 // originals => include extended 93 public static IEnumerable<string> ExtendVariables(IEnumerable<string> variables, IEnumerable<IDataAnalysisTransformation> transformations) { 94 return GetTransitiveVariables(variables, transformations); 95 } 96 97 // extended => originals 98 public static IEnumerable<string> ReduceVariables(IEnumerable<string> variables, IEnumerable<IDataAnalysisTransformation> transformations) { 99 var originalVariables = new HashSet<string>(); 100 foreach (var variable in variables) 101 originalVariables.Add(GetLastTransitiveVariable(variable, transformations, inverse: true)); 102 return originalVariables; 103 } 104 105 public static IEnumerable<string> GetTransitiveVariables(IEnumerable<string> variables, IEnumerable<IDataAnalysisTransformation> transformations, bool inverse = false) { 106 var reachableVariables = new HashSet<string>(variables); 107 if (inverse) transformations = transformations.Reverse(); 108 foreach (var transformation in transformations) { 109 var source = inverse ? transformation.TransformedVariable : transformation.OriginalVariable; 110 var target = inverse ? transformation.OriginalVariable : transformation.TransformedVariable; 111 if (reachableVariables.Contains(source)) 112 reachableVariables.Add(target); 113 } 114 115 return reachableVariables; 116 } 117 118 public static string GetLastTransitiveVariable(string variable, IEnumerable<IDataAnalysisTransformation> transformations, bool inverse = false) { 119 if (inverse) transformations = transformations.Reverse(); 120 foreach (var transformation in transformations) { 121 var source = inverse ? transformation.TransformedVariable : transformation.OriginalVariable; 122 var target = inverse ? transformation.OriginalVariable : transformation.TransformedVariable; 123 if (variable == source) 124 variable = target; 125 } 126 127 return variable; 128 } 129 #endregion 130 131 #region Transform Dataset 132 public static IDataset Transform(IDataset dataset, IEnumerable<IDataAnalysisTransformation> transformations) { 133 var modifiableDataset = ((Dataset)dataset).ToModifiable(); 134 135 foreach (var transformation in transformations) { 136 var trans = (ITransformation<double>)transformation.Transformation; 137 138 var originalData = modifiableDataset.GetDoubleValues(transformation.OriginalVariable); 139 //if (!trans.Check(originalData, out string errorMessage)) 140 // throw new InvalidOperationException($"Cannot estimate Values, Transformation is invalid: {errorMessage}"); 141 // TODO: check was already called before configure (in preprocessing) 142 // TODO: newly specified data might not pass the check but it does not matter because the data is not configured with 143 // e.g. impact calculation -> replacement=most common -> originalMean is zero 144 145 var transformedData = trans.Apply(originalData).ToList(); 146 if (modifiableDataset.VariableNames.Contains(transformation.TransformedVariable)) 147 modifiableDataset.ReplaceVariable(transformation.TransformedVariable, transformedData); 148 else 149 modifiableDataset.AddVariable(transformation.TransformedVariable, transformedData); 150 } 151 152 return modifiableDataset; // TODO: to regular dataset? 153 } 154 155 public static IDataset InverseTransform(IDataset dataset, IEnumerable<IDataAnalysisTransformation> transformations, bool removeVirtualVariables = true) { 156 var modifiableDataset = ((Dataset)dataset).ToModifiable(); 157 158 var transformationsStack = new Stack<IDataAnalysisTransformation>(transformations); 159 while (transformationsStack.Any()) { 160 var transformation = transformationsStack.Pop(); 161 var trans = (ITransformation<double>)transformation.Transformation; 162 163 var prevTransformations = transformations.Except(transformationsStack); 164 bool originalWasChanged = prevTransformations.Any(x => x.TransformedVariable == transformation.OriginalVariable); 165 if (originalWasChanged) { 166 var transformedData = modifiableDataset.GetDoubleValues(transformation.TransformedVariable); 167 168 var originalData = trans.InverseApply(transformedData).ToList(); 169 modifiableDataset.ReplaceVariable(transformation.OriginalVariable, originalData); 170 } 171 } 172 173 if (removeVirtualVariables) { 174 var originalVariables = ReduceVariables(dataset.VariableNames, transformations); 175 var virtualVariables = dataset.VariableNames.Except(originalVariables); 176 foreach (var virtualVariable in virtualVariables) 177 modifiableDataset.RemoveVariable(virtualVariable); 178 } 179 180 return modifiableDataset; // TODO: to regular dataset? 181 } 182 #endregion 183 184 #region Transform ProblemData 185 public static IDataAnalysisProblemData ApplyTransformations(IDataAnalysisProblemData problemData) { 186 var newDataset = Transform(problemData.Dataset, problemData.Transformations); 187 var extendedInputs = ExtendVariables(problemData.AllowedInputVariables, problemData.Transformations); 188 189 return CreateNewProblemData(problemData, newDataset, extendedInputs, inverse: false); 190 } 191 192 public static IDataAnalysisProblemData InverseApplyTransformations(IDataAnalysisProblemData problemData) { 193 var newDataset = InverseTransform(problemData.Dataset, problemData.Transformations); 194 var reducedInputs = ReduceVariables(problemData.AllowedInputVariables, problemData.Transformations); 195 196 return CreateNewProblemData(problemData, newDataset, reducedInputs, inverse: true); 197 } 198 199 private static IDataAnalysisProblemData CreateNewProblemData(IDataAnalysisProblemData problemData, IDataset dataset, IEnumerable<string> inputs, bool inverse = false) { 200 IDataAnalysisProblemData newProblemData; 201 if (problemData is IRegressionProblemData regressionProblemData) { 202 var newTargetVariable = GetLastTransitiveVariable(regressionProblemData.TargetVariable, problemData.Transformations, inverse); 203 newProblemData = new RegressionProblemData(dataset, inputs, newTargetVariable, problemData.Transformations); 204 } else if (problemData is IClassificationProblemData classificationProblemData) { 205 newProblemData = new ClassificationProblemData(dataset, inputs, classificationProblemData.TargetVariable, problemData.Transformations); 206 } else throw new NotSupportedException("Type of ProblemData not supported"); 207 208 newProblemData.TrainingPartition.Start = problemData.TrainingPartition.Start; 209 newProblemData.TrainingPartition.End = problemData.TrainingPartition.End; 210 newProblemData.TestPartition.Start = problemData.TestPartition.Start; 211 newProblemData.TestPartition.End = problemData.TestPartition.End; 212 213 return newProblemData; 214 } 215 #endregion 216 217 #region Transform Model 218 public static IDataAnalysisTransformationModel CreateTransformationIntegratedModel(IDataAnalysisModel model, IEnumerable<IDataAnalysisTransformation> transformations) { 219 if (model is IDataAnalysisTransformationModel) 220 throw new InvalidOperationException("Model already is a transformation model."); 221 222 switch (model) { 223 case ITimeSeriesPrognosisModel timeSeriesPrognosisModel: 224 return new TimeSeriesPrognosisTransformationModel(timeSeriesPrognosisModel, transformations); 225 case IRegressionModel regressionModel: 226 return new RegressionTransformationModel(regressionModel, transformations); 227 case IClassificationModel classificationModel: 228 return new ClassificationTransformationModel(classificationModel, transformations); 229 case IClusteringModel clusteringModel: 230 return new ClusteringTransformationModel(clusteringModel, transformations); 231 default: 232 throw new NotSupportedException("Type of the model is not supported;"); 233 } 234 } 235 236 public static IDataAnalysisModel RestoreTrainedModel(IDataAnalysisModel transformationModel, IEnumerable<IDataAnalysisTransformation> transformations) { 237 if (!(transformationModel is IDataAnalysisTransformationModel model)) 238 throw new InvalidOperationException("Cannot restore because model is not a TransformationModel"); 239 return model.OriginalModel; 240 } 241 #endregion 242 243 #region Transform Solution 244 public static IDataAnalysisSolution TransformSolution(IDataAnalysisSolution solution) { 245 var transformations = solution.ProblemData.Transformations; 246 247 var model = solution.Model is IDataAnalysisTransformationModel // TODO: what if model is a integrated sym-reg model? 248 ? RestoreTrainedModel(solution.Model, transformations) 249 : CreateTransformationIntegratedModel(solution.Model, transformations); 250 251 var data = solution.Model is IDataAnalysisTransformationModel 252 ? ApplyTransformations(solution.ProblemData) // original -> transformed 253 : InverseApplyTransformations(solution.ProblemData); // transformed -> original 254 255 return CreateSolution(model, data); 256 } 257 258 private static IDataAnalysisSolution CreateSolution(IDataAnalysisModel model, IDataAnalysisProblemData problemData) { 259 switch (model) { 260 case ITimeSeriesPrognosisModel timeSeriesPrognosisModel: 261 return timeSeriesPrognosisModel.CreateTimeSeriesPrognosisSolution((ITimeSeriesPrognosisProblemData)problemData); 262 case IRegressionModel regressionModel: 263 return regressionModel.CreateRegressionSolution((IRegressionProblemData)problemData); 264 case IClassificationModel classificationModel: 265 return classificationModel.CreateClassificationSolution((IClassificationProblemData)problemData); 266 default: 267 throw new NotSupportedException("Cannot create Solution of the model type."); 268 } 269 } 270 #endregion 271 272 #endregion 86 273 } 87 274 } -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/DataAnalysisTransformationModel.cs
r15880 r15884 35 35 public IDataAnalysisModel OriginalModel { get; protected set; } 36 36 37 IEnumerable<IDataAnalysisTransformation> IDataAnalysisTransformationModel.InputTransformations { 38 get { return InputTransformations; } 39 } 40 37 41 [Storable] 38 42 public ReadOnlyItemList<IDataAnalysisTransformation> InputTransformations { get; protected set; } … … 55 59 56 60 public override IEnumerable<string> VariablesUsedForPrediction { 57 get { return OriginalModel.VariablesUsedForPrediction; /* TODO: reduce extend-inputs */}61 get { return DataAnalysisTransformation.ReduceVariables(OriginalModel.VariablesUsedForPrediction, InputTransformations); } 58 62 } 59 63 60 64 #region Constructor, Cloning & Persistence 61 65 protected DataAnalysisTransformationModel(IDataAnalysisModel originalModel, IEnumerable<IDataAnalysisTransformation> transformations) 62 : base( originalModel.Name) {66 : base("Transformation Model " + originalModel.Name) { 63 67 OriginalModel = originalModel; 64 var transitiveInputs = CalculateTransitiveVariables(originalModel.VariablesUsedForPrediction, transformations);68 var transitiveInputs = DataAnalysisTransformation.GetTransitiveVariables(originalModel.VariablesUsedForPrediction, transformations, inverse: true); 65 69 InputTransformations = new ItemList<IDataAnalysisTransformation>(transformations.Where(t => transitiveInputs.Contains(t.OriginalVariable))).AsReadOnly(); 66 70 TargetTransformations = new ReadOnlyItemList<IDataAnalysisTransformation>(); … … 80 84 #endregion 81 85 82 // extended -> include originals83 public static ISet<string> CalculateTransitiveVariables(IEnumerable<string> inputVariables, IEnumerable<IDataAnalysisTransformation> transformations) {84 var transitiveInputs = new HashSet<string>(inputVariables);85 86 foreach (var transformation in transformations.Reverse()) {87 if (transitiveInputs.Contains(transformation.TransformedVariable)) {88 transitiveInputs.Add(transformation.OriginalVariable);89 }90 }91 92 return transitiveInputs;93 }94 // originals => include extended95 public static IEnumerable<string> ExtendInputVariables(IEnumerable<string> oldInputVariables, IEnumerable<IDataAnalysisTransformation> transformations) {96 var inputs = new HashSet<string>(oldInputVariables);97 98 foreach (var transformation in transformations) {99 if (inputs.Contains(transformation.OriginalVariable))100 inputs.Add(transformation.TransformedVariable);101 }102 103 return inputs;104 }105 [Obsolete]106 public static IEnumerable<string> RemoveVirtualVariables(IEnumerable<string> variables, IEnumerable<IDataAnalysisTransformation> transformations) {107 var remainingVariables = new HashSet<string>(variables);108 109 var transformationsStack = new Stack<IDataAnalysisTransformation>(transformations);110 111 while (transformationsStack.Any()) {112 var transformation = transformationsStack.Pop();113 114 115 bool transformedVariablePending = transformationsStack.Any(x => x.OriginalVariable == transformation.TransformedVariable);116 if (!transformedVariablePending)117 remainingVariables.Remove(transformation.TransformedVariable);118 }119 120 return remainingVariables;121 }122 123 public static IDataset Transform(IDataset dataset, IEnumerable<IDataAnalysisTransformation> transformations) {124 var modifiableDataset = ((Dataset)dataset).ToModifiable();125 126 foreach (var transformation in transformations) {127 var trans = (ITransformation<double>)transformation.Transformation;128 129 var originalData = modifiableDataset.GetDoubleValues(transformation.OriginalVariable);130 if (!trans.Check(originalData, out string errorMessage))131 throw new InvalidOperationException($"Cannot estimate Values, Transformation is invalid: {errorMessage}");132 133 var transformedData = trans.Apply(originalData).ToList();134 if (modifiableDataset.VariableNames.Contains(transformation.TransformedVariable))135 modifiableDataset.ReplaceVariable(transformation.TransformedVariable, transformedData);136 else137 modifiableDataset.AddVariable(transformation.TransformedVariable, transformedData);138 }139 140 return modifiableDataset;141 }142 143 86 #region Events 144 87 public event EventHandler TargetVariableChanged; -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Regression/RegressionProblemData.cs
r15870 r15884 180 180 base.AdjustProblemDataProperties(problemData); 181 181 } 182 183 public override IDataAnalysisProblemData Transform() {184 var transformedProblemData = (IRegressionProblemData)base.Transform();185 var targetVariable = RegressionTransformationModel.GetTransformedTragetVariable(TargetVariable, Transformations);186 transformedProblemData.TargetVariable = targetVariable;187 return transformedProblemData;188 }189 190 public override IDataAnalysisProblemData InverseTransform() {191 var transformedProblemData = (IRegressionProblemData)base.InverseTransform();192 var targetVariable = RegressionTransformationModel.GetOriginalTragetVariable(TargetVariable, Transformations);193 transformedProblemData.TargetVariable = targetVariable;194 return transformedProblemData;195 }196 182 } 197 183 } -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Regression/RegressionTransformationModel.cs
r15870 r15884 20 20 #endregion 21 21 22 using System;23 22 using System.Collections.Generic; 24 23 using System.Linq; … … 36 35 } 37 36 37 IEnumerable<IDataAnalysisTransformation> IRegressionTransformationModel.TargetTransformations { 38 get { return TargetTransformations; } 39 } 40 38 41 #region Constructor, Cloning & Persistence 39 42 public RegressionTransformationModel(IRegressionModel originalModel, IEnumerable<IDataAnalysisTransformation> transformations) 40 43 : base(originalModel, transformations) { 41 var transitiveTargets = CalculateTransitiveVariables(new[] { originalModel.TargetVariable }, transformations);44 var transitiveTargets = DataAnalysisTransformation.GetTransitiveVariables(new[] { originalModel.TargetVariable }, transformations, inverse: true).ToList(); 42 45 TargetTransformations = new ItemList<IDataAnalysisTransformation>(transformations.Where(t => transitiveTargets.Contains(t.OriginalVariable))).AsReadOnly(); 43 TargetVariable = GetOriginalTragetVariable(originalModel.TargetVariable, TargetTransformations);46 TargetVariable = DataAnalysisTransformation.GetLastTransitiveVariable(originalModel.TargetVariable, TargetTransformations, inverse: true); 44 47 } 45 48 46 49 protected RegressionTransformationModel(RegressionTransformationModel original, Cloner cloner) 47 50 : base(original, cloner) { 48 49 51 } 50 52 … … 59 61 60 62 public virtual IEnumerable<double> GetEstimatedValues(IDataset dataset, IEnumerable<int> rows) { 61 var estimates = OriginalModel.GetEstimatedValues(Transform(dataset, InputTransformations), rows); 62 return InverseTransform(estimates, TargetTransformations, OriginalModel.TargetVariable); 63 var transformedInput = DataAnalysisTransformation.Transform(dataset, InputTransformations); 64 var estimates = OriginalModel.GetEstimatedValues(transformedInput, rows); 65 return InverseTransform(estimates, TargetTransformations); 63 66 } 64 67 … … 67 70 } 68 71 69 public static IEnumerable<double> InverseTransform(IEnumerable<double> data, IEnumerable<IDataAnalysisTransformation> transformations, string targetVariable) { 70 var estimates = data.ToList(); 71 72 foreach (var transformation in transformations.Reverse()) { 73 if (transformation.TransformedVariable == targetVariable) { 74 var trans = (ITransformation<double>)transformation.Transformation; 75 76 estimates = trans.InverseApply(estimates).ToList(); 77 78 // setup next iteration 79 targetVariable = transformation.OriginalVariable; 80 } 72 protected static IEnumerable<double> InverseTransform(IEnumerable<double> data, IEnumerable<IDataAnalysisTransformation> transformations) { 73 foreach (var transformation in transformations.Reverse()) { // TargetTransformations only contains only relevant transformations 74 var trans = (ITransformation<double>)transformation.Transformation; 75 data = trans.InverseApply(data).ToList(); 81 76 } 82 83 return estimates; 84 } 85 86 public static string GetTransformedTragetVariable(string originalTarget, IEnumerable<IDataAnalysisTransformation> transformations) { 87 var transformedTarget = originalTarget; 88 foreach (var transformation in transformations) { 89 if (transformation.OriginalVariable == transformedTarget) 90 transformedTarget = transformation.TransformedVariable; 91 } 92 return transformedTarget; 93 } 94 95 public static string GetOriginalTragetVariable(string transformedTarget, IEnumerable<IDataAnalysisTransformation> transformations) { 96 var originalTarget = transformedTarget; 97 foreach (var transformation in transformations.Reverse()) { 98 if (transformation.TransformedVariable == originalTarget) 99 originalTarget = transformation.OriginalVariable; 100 } 101 return originalTarget; 77 return data; 102 78 } 103 79 } -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/TimeSeriesPrognosis/Models/TimeSeriesPrognosisTransformationModel.cs
r15870 r15884 53 53 #endregion 54 54 55 55 56 public IEnumerable<IEnumerable<double>> GetPrognosedValues(IDataset dataset, IEnumerable<int> rows, IEnumerable<int> horizons) { 56 var estimates = OriginalModel.GetPrognosedValues(Transform(dataset, InputTransformations), rows, horizons); 57 return estimates.Select(x => InverseTransform(x, TargetTransformations, TargetVariable)); // TODO: transform the whole horizon? 57 var transformedInput = DataAnalysisTransformation.Transform(dataset, InputTransformations); 58 var estimates = OriginalModel.GetPrognosedValues(transformedInput, rows, horizons); 59 return estimates.Select(x => InverseTransform(x, TargetTransformations)); 58 60 } 59 61 -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Transformations/LinearTransformation.cs
r15865 r15884 20 20 #endregion 21 21 22 using System; 22 23 using System.Collections.Generic; 23 24 using System.Linq; … … 46 47 public double Slope { 47 48 get { return SlopeParameter.Value.Value; } 48 set { SlopeParameter.Value.Value = value; } //TODO: check for != 0?49 set { SlopeParameter.Value.Value = value; } 49 50 } 50 51 … … 85 86 86 87 public static IEnumerable<double> Apply(IEnumerable<double> data, double slope = 1.0, double intercept = 0.0) { 88 if (slope.IsAlmost(0.0)) 89 throw new InvalidOperationException($"Cannot transform with a {nameof(slope)} of zero because inverse transformation would be invalid."); 90 87 91 return data.Select(x => slope * x + intercept); 88 92 } 89 93 90 94 public static IEnumerable<double> InverseApply(IEnumerable<double> data, double slope = 1.0, double intercept = 0.0) { 95 if (slope.IsAlmost(0.0)) 96 throw new InvalidOperationException($"Cannot inverse transform with a {nameof(slope)} of zero."); 97 91 98 return data.Select(x => (x - intercept) / slope); 92 99 } -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis/3.4/Implementation/Transformations/ZNormalizationTransformation.cs
r15865 r15884 20 20 #endregion 21 21 22 using System; 22 23 using System.Collections.Generic; 23 24 using System.Linq; … … 97 98 98 99 public override void Configure(IEnumerable<double> data) { 99 OriginalMean = data.Average(); 100 OriginalStandardDeviation = data.StandardDeviationPop(); 100 Configure(data, out double originalMean, out double originalStandardDeviation); 101 OriginalMean = originalMean; 102 OriginalStandardDeviation = originalStandardDeviation; 101 103 base.Configure(data); 102 104 } 103 105 104 106 public override IEnumerable<double> Apply(IEnumerable<double> data) { 105 if (double.IsNaN(OriginalMean) || double.IsNaN(OriginalStandardDeviation)) //TODO isConfigured field?106 Configure(data);107 if (double.IsNaN(OriginalMean) || double.IsNaN(OriginalStandardDeviation)) 108 throw new InvalidOperationException("Transformation is not configured"); 107 109 108 110 return Apply(data, TargetMean, TargetStandardDeviation, OriginalMean, OriginalStandardDeviation); … … 110 112 111 113 public override IEnumerable<double> InverseApply(IEnumerable<double> data) { 114 if (double.IsNaN(OriginalMean) || double.IsNaN(OriginalStandardDeviation)) 115 throw new InvalidOperationException("Transformation is not configured"); 116 112 117 return InverseApply(data, TargetMean, TargetStandardDeviation, OriginalMean, OriginalStandardDeviation); 113 118 } 114 119 120 121 public static void Configure(IEnumerable<double> data, out double originalMean, out double originalStandardDeviation) { 122 originalMean = data.Average(); 123 originalStandardDeviation = data.StandardDeviationPop(); 124 } 115 125 116 126 public static IEnumerable<double> Apply(IEnumerable<double> data, double targetMean, double targetStandardDeviation, double originalMean = double.NaN, double originalStandardDeviation = double.NaN) { -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis/3.4/Interfaces/IDataAnalysisProblemData.cs
r15856 r15884 44 44 45 45 IEnumerable<IDataAnalysisTransformation> Transformations { get; } 46 IDataAnalysisProblemData Transform();47 IDataAnalysisProblemData InverseTransform();48 46 49 47 bool IsTrainingSample(int index); -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis/3.4/Interfaces/IDataAnalysisTransformationModel.cs
r15870 r15884 20 20 #endregion 21 21 22 using HeuristicLab.Core;22 using System.Collections.Generic; 23 23 24 24 namespace HeuristicLab.Problems.DataAnalysis { … … 28 28 /// <summary> 29 29 /// Transformations that are used on the model's inputs. 30 /// </summary> 31 ReadOnlyItemList<IDataAnalysisTransformation> InputTransformations { get; } // TODO: IReadonlyList<>? 32 33 ReadOnlyItemList<IDataAnalysisTransformation> TargetTransformations { get; } // TODO: to Regression/Classification interface? 30 /// </summary> 31 IEnumerable<IDataAnalysisTransformation> InputTransformations { get; } 34 32 } 35 33 } -
branches/2906_Transformations/HeuristicLab.Problems.DataAnalysis/3.4/Interfaces/Regression/IRegressionTransformationModel.cs
r15870 r15884 20 20 #endregion 21 21 22 using HeuristicLab.Core;22 using System.Collections.Generic; 23 23 24 24 namespace HeuristicLab.Problems.DataAnalysis { 25 25 public interface IRegressionTransformationModel : IDataAnalysisTransformationModel, IRegressionModel { 26 26 new IRegressionModel OriginalModel { get; } 27 28 IEnumerable<IDataAnalysisTransformation> TargetTransformations { get; } 27 29 } 28 30 }
Note: See TracChangeset
for help on using the changeset viewer.