Free cookie consent management tool by TermsFeed Policy Generator

source: branches/3.1/sources/HeuristicLab.Functions/Variable.cs @ 7140

Last change on this file since 7140 was 470, checked in by gkronber, 16 years ago

fixed the range for uniform random numbers in the initializer for index and sample-offset of variable (necessary after fixing #238) (ticket #237)

File size: 9.2 KB
Line 
1#region License Information
2/* HeuristicLab
3 * Copyright (C) 2002-2008 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.Collections.Generic;
24using System.Text;
25using HeuristicLab.Core;
26using System.Diagnostics;
27using HeuristicLab.Data;
28using HeuristicLab.Constraints;
29using HeuristicLab.DataAnalysis;
30using HeuristicLab.Random;
31using HeuristicLab.Operators;
32
33namespace HeuristicLab.Functions {
34  public class Variable : FunctionBase {
35
36    public const string WEIGHT = "Weight";
37    public const string OFFSET = "SampleOffset";
38    public const string INDEX = "Variable";
39
40    private int minIndex;
41    private int maxIndex;
42    private int minOffset;
43    private int maxOffset;
44
45    public override string Description {
46      get {
47        return @"Variable reads a value from a dataset, multiplies that value with a given factor and returns the result.
48The variable 'SampleOffset' can be used to read a value from previous or following rows.
49The index of the row that is actually read is SampleIndex+SampleOffset).";
50      }
51    }
52
53    public Variable()
54      : base() {
55      AddVariableInfo(new VariableInfo(INDEX, "Index of the variable in the dataset representing this feature", typeof(ConstrainedIntData), VariableKind.None));
56      GetVariableInfo(INDEX).Local = true;
57      AddVariableInfo(new VariableInfo(WEIGHT, "Weight is multiplied to the feature value", typeof(ConstrainedDoubleData), VariableKind.None));
58      GetVariableInfo(WEIGHT).Local = true;
59      AddVariableInfo(new VariableInfo(OFFSET, "SampleOffset is added to the sample index", typeof(ConstrainedIntData), VariableKind.None));
60      GetVariableInfo(OFFSET).Local = true;
61      AddVariableInfo(new VariableInfo(INITIALIZATION, "Initialization operator for variables", typeof(CombinedOperator), VariableKind.None));
62      GetVariableInfo(INITIALIZATION).Local = false;
63      AddVariableInfo(new VariableInfo(MANIPULATION, "Manipulation operator for variables", typeof(CombinedOperator), VariableKind.None));
64      GetVariableInfo(MANIPULATION).Local = false;
65
66      ConstrainedDoubleData weight = new ConstrainedDoubleData();
67      // initialize a totally arbitrary range for the weight = [-20.0, 20.0]
68      weight.AddConstraint(new DoubleBoundedConstraint(-20.0, 20.0));
69      AddVariable(new HeuristicLab.Core.Variable(WEIGHT, weight));
70
71      ConstrainedIntData variable = new ConstrainedIntData();
72      AddVariable(new HeuristicLab.Core.Variable(INDEX, variable));
73      minIndex = 0; maxIndex = 100;
74
75      ConstrainedIntData sampleOffset = new ConstrainedIntData();
76      AddVariable(new HeuristicLab.Core.Variable(OFFSET, sampleOffset));
77
78      SetupInitialization();
79      SetupManipulation();
80
81      // variable can't have suboperators
82      AddConstraint(new NumberOfSubOperatorsConstraint(0, 0));
83    }
84
85    private void SetupInitialization() {
86      CombinedOperator combinedOp = new CombinedOperator();
87      SequentialProcessor seq = new SequentialProcessor();
88      UniformRandomizer indexRandomizer = new UniformRandomizer();
89      indexRandomizer.Min = minIndex;
90      indexRandomizer.Max = maxIndex + 1; // uniform randomizer generates numbers in the range [min, max[
91      indexRandomizer.GetVariableInfo("Value").ActualName = INDEX;
92      indexRandomizer.Name = "Index Randomizer";
93      NormalRandomizer weightRandomizer = new NormalRandomizer();
94      weightRandomizer.Mu = 1.0;
95      weightRandomizer.Sigma = 1.0;
96      weightRandomizer.GetVariableInfo("Value").ActualName = WEIGHT;
97      weightRandomizer.Name = "Weight Randomizer";
98      UniformRandomizer offsetRandomizer = new UniformRandomizer();
99      offsetRandomizer.Min = minOffset;
100      offsetRandomizer.Max = maxOffset + 1;
101      offsetRandomizer.GetVariableInfo("Value").ActualName = OFFSET;
102      offsetRandomizer.Name = "Offset Randomizer";
103
104      combinedOp.OperatorGraph.AddOperator(seq);
105      combinedOp.OperatorGraph.AddOperator(indexRandomizer);
106      combinedOp.OperatorGraph.AddOperator(weightRandomizer);
107      combinedOp.OperatorGraph.AddOperator(offsetRandomizer);
108      combinedOp.OperatorGraph.InitialOperator = seq;
109      seq.AddSubOperator(indexRandomizer);
110      seq.AddSubOperator(weightRandomizer);
111      seq.AddSubOperator(offsetRandomizer);
112      HeuristicLab.Core.IVariable initOp = GetVariable(INITIALIZATION);
113      if(initOp == null) {
114        AddVariable(new HeuristicLab.Core.Variable(INITIALIZATION, combinedOp));
115      } else {
116        initOp.Value = combinedOp;
117      }
118    }
119
120    private void SetupManipulation() {
121      // manipulation operator
122      CombinedOperator combinedOp = new CombinedOperator();
123      SequentialProcessor seq = new SequentialProcessor();
124      UniformRandomizer indexRandomizer = new UniformRandomizer();
125      indexRandomizer.Min = minIndex;
126      indexRandomizer.Max = maxIndex + 1;
127      indexRandomizer.GetVariableInfo("Value").ActualName = INDEX;
128      indexRandomizer.Name = "Index Randomizer";
129      NormalRandomAdder weightRandomAdder = new NormalRandomAdder();
130      weightRandomAdder.Mu = 0.0;
131      weightRandomAdder.Sigma = 0.1;
132      weightRandomAdder.GetVariableInfo("Value").ActualName = WEIGHT;
133      weightRandomAdder.Name = "Weight Adder";
134      NormalRandomAdder offsetRandomAdder = new NormalRandomAdder();
135      offsetRandomAdder.Mu = 0.0;
136      offsetRandomAdder.Sigma = 1.0;
137      offsetRandomAdder.GetVariableInfo("Value").ActualName = OFFSET;
138      offsetRandomAdder.Name = "Offset Adder";
139
140      combinedOp.OperatorGraph.AddOperator(seq);
141      combinedOp.OperatorGraph.AddOperator(indexRandomizer);
142      combinedOp.OperatorGraph.AddOperator(weightRandomAdder);
143      combinedOp.OperatorGraph.AddOperator(offsetRandomAdder);
144      combinedOp.OperatorGraph.InitialOperator = seq;
145      seq.AddSubOperator(indexRandomizer);
146      seq.AddSubOperator(weightRandomAdder);
147      seq.AddSubOperator(offsetRandomAdder);
148      HeuristicLab.Core.IVariable manipulationOp = GetVariable(MANIPULATION);
149      if(manipulationOp == null) {
150        AddVariable(new HeuristicLab.Core.Variable(MANIPULATION, combinedOp));
151      } else {
152        manipulationOp.Value = combinedOp;
153      }
154    }
155
156    public void SetConstraints(int[] allowedIndexes, int minSampleOffset, int maxSampleOffset) {
157      ConstrainedIntData offset = GetVariableValue<ConstrainedIntData>(OFFSET, null, false);
158      IntBoundedConstraint rangeConstraint = new IntBoundedConstraint();
159      this.minOffset = minSampleOffset;
160      this.maxOffset = maxSampleOffset;
161      rangeConstraint.LowerBound = minSampleOffset;
162      rangeConstraint.LowerBoundEnabled = true;
163      rangeConstraint.LowerBoundIncluded = true;
164      rangeConstraint.UpperBound = maxSampleOffset;
165      rangeConstraint.UpperBoundEnabled = true;
166      rangeConstraint.UpperBoundIncluded = true;
167      offset.AddConstraint(rangeConstraint);
168
169      ConstrainedIntData index = GetVariableValue<ConstrainedIntData>(INDEX, null, false);
170      Array.Sort(allowedIndexes);
171      minIndex = allowedIndexes[0]; maxIndex = allowedIndexes[allowedIndexes.Length - 1];
172      List<IConstraint> constraints = new List<IConstraint>();
173      int start = allowedIndexes[0];
174      int prev = start;
175      for(int i = 1; i < allowedIndexes.Length; i++) {
176        if(allowedIndexes[i] != prev + 1) {
177          IntBoundedConstraint lastRange = new IntBoundedConstraint();
178          lastRange.LowerBound = start;
179          lastRange.LowerBoundEnabled = true;
180          lastRange.LowerBoundIncluded = true;
181          lastRange.UpperBound = prev;
182          lastRange.UpperBoundEnabled = true;
183          lastRange.UpperBoundIncluded = true;
184          constraints.Add(lastRange);
185          start = allowedIndexes[i];
186          prev = start;
187        }
188        prev = allowedIndexes[i];
189      }
190      IntBoundedConstraint range = new IntBoundedConstraint();
191      range.LowerBound = start;
192      range.LowerBoundEnabled = true;
193      range.LowerBoundIncluded = true;
194      range.UpperBound = prev;
195      range.UpperBoundEnabled = true;
196      range.UpperBoundIncluded = true;
197      constraints.Add(range);
198      if(constraints.Count > 1) {
199        OrConstraint or = new OrConstraint();
200        foreach(IConstraint c in constraints) or.Clauses.Add(c);
201        index.AddConstraint(or);
202      } else {
203        index.AddConstraint(constraints[0]);
204      }
205
206      SetupInitialization();
207      SetupManipulation();
208    }
209
210    public override void Accept(IFunctionVisitor visitor) {
211      visitor.Visit(this);
212    }
213  }
214}
Note: See TracBrowser for help on using the repository browser.