#region License Information /* HeuristicLab * Copyright (C) 2002-2016 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 . */ #endregion using System; using System.Collections.Generic; using System.Linq; using System.Text; using HeuristicLab.Collections; using HeuristicLab.Common; using HeuristicLab.Core; using HeuristicLab.Data; using HeuristicLab.Encodings.RealVectorEncoding; using HeuristicLab.Problems.DataAnalysis; namespace HeuristicLab.GoalSeeking { internal static class GoalSeekingUtil { internal static void UpdateTargets(ICheckedItemList goals, IEnumerable models, EventHandler changedEventHandler) { var targets = models.Select(x => x.TargetVariable).Distinct().OrderBy(x => x); var dict = goals.ToDictionary(x => x.Name, x => x); goals.Clear(); foreach (var t in targets) { GoalParameter gp; if (dict.ContainsKey(t)) { gp = dict[t]; } else { var goal = double.NaN; var weight = 1.0; var variance = double.NaN; var step = 1e-6; gp = new GoalParameter(t, goal, weight, variance, step, active: false); // new goals are not active by default as they need to be configured by the user gp.Changed += changedEventHandler; } goals.Add(gp, gp.Active); } } internal static void UpdateInputs(ICheckedItemList inputs, IEnumerable models, EventHandler changedEventHandler) { var variables = models.SelectMany(x => x.VariablesUsedForPrediction).Distinct(); var dict = inputs.ToDictionary(x => x.Name, x => x); // save old parameter settings inputs.Clear(); foreach (var v in variables) { InputParameter ip; if (dict.ContainsKey(v)) { ip = dict[v]; } else { ip = new InputParameter(v, double.NaN, -1, 1, 1e-6, active: false); // new inputs are not active by default. the user needs to configure them first ip.Changed += changedEventHandler; } inputs.Add(ip, ip.Active); } } internal static RealVectorEncoding CreateEncoding(IEnumerable inputParameters) { var encoding = new RealVectorEncoding(inputParameters.Count()); encoding.Bounds = new DoubleMatrix(encoding.Length, 2); // only two columns: min and max encoding.Bounds.RowNames = inputParameters.Select(x => x.Name); encoding.Bounds.ColumnNames = new[] { "Min.", "Max." }; int i = 0; foreach (var parameter in inputParameters) { encoding.Bounds[i, 0] = parameter.Min; encoding.Bounds[i, 1] = parameter.Max; ++i; } return encoding; } internal static void UpdateEncoding(RealVectorEncoding encoding, IEnumerable inputParameters) { encoding.Length = inputParameters.Count(); encoding.Bounds = new DoubleMatrix(encoding.Length, 2); encoding.Bounds.RowNames = inputParameters.Select(x => x.Name); encoding.Bounds.ColumnNames = new[] { "Min.", "Max." }; int i = 0; foreach (var parameter in inputParameters) { encoding.Bounds[i, 0] = parameter.Min; encoding.Bounds[i, 1] = parameter.Max; ++i; } } internal static void ValidateGoalsAndInputs(IEnumerable goals, IEnumerable inputs) { var notConfiguredGoals = goals.Where(x => x.Active && (double.IsNaN(x.Variance) || double.IsNaN(x.Goal))).ToList(); var notConfiguredInputs = inputs.Where(x => x.Active && (double.IsNaN(x.Min) || double.IsNaN(x.Max) || double.IsNaN(x.Value))).ToList(); StringBuilder sb = null; if (notConfiguredGoals.Any()) { sb = new StringBuilder(); sb.AppendLine("The following GoalParameters are not configured."); foreach (var goal in notConfiguredGoals) { sb.AppendLine(goal.Name); } } if (notConfiguredInputs.Any()) { if (sb == null) sb = new StringBuilder(); sb.AppendLine("The following InpuTParameters are not configured."); foreach (var input in notConfiguredInputs) { sb.AppendLine(input.Name); } } if (sb != null) throw new InvalidOperationException(sb.ToString()); } internal static void Configure(IEnumerable goals, IEnumerable inputs, IRegressionProblemData problemData, int row) { var inputMap = inputs.ToDictionary(x => x.Name, x => x); var goalMap = goals.ToDictionary(x => x.Name, x => x); foreach (var variable in problemData.Dataset.DoubleVariables) { if (inputMap.ContainsKey(variable)) { var values = problemData.Dataset.GetReadOnlyDoubleValues(variable); var input = inputMap[variable]; input.Value = values[row]; double min = values[0], max = values[0]; foreach (var v in values) { if (min > v) min = v; if (max < v) max = v; } input.Min = min; input.Max = max; } else if (goalMap.ContainsKey(variable)) { var values = problemData.Dataset.GetReadOnlyDoubleValues(variable); var goal = goalMap[variable]; goal.Variance = values.Variance(); goal.Goal = values[row]; } } } internal static void Goals_CheckedItemsChanged(object sender, CollectionItemsChangedEventArgs> args) { var goals = (CheckedItemList)sender; foreach (var item in args.Items.Select(x => x.Value)) { item.Active = goals.ItemChecked(item); } } internal static void Inputs_CheckedItemsChanged(object sender, CollectionItemsChangedEventArgs> args) { var inputs = (CheckedItemList)sender; foreach (var item in args.Items.Select(x => x.Value)) { item.Active = inputs.ItemChecked(item); } } internal static void RaiseEvent(object sender, EventHandler handler) { if (handler == null) return; handler(sender, EventArgs.Empty); } } }