source: scolib/trunk/scolib/DomainOpsIntArray.h @ 5797

Revision 5797, 6.3 KB checked in by wehart, 5 years ago (diff)

Renaming coliny -> scolib. :)

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
Line 
1/*  _________________________________________________________________________
2 *
3 *  Coliny: A Library of COLIN optimizers
4 *  Copyright (c) 2003, Sandia National Laboratories.
5 *  This software is distributed under the GNU Lesser General Public License.
6 *  For more information, see the README.html file in the top Coliny directory.
7 *  _________________________________________________________________________
8 */
9
10/**
11 * \file DomainOpsIntArray.h
12 *
13 * Defines the scolib::DomainOpsIntArray class.
14 */
15
16#ifndef scolib_DomainIntOpsArray_h
17#define scolib_DomainIntOpsArray_h
18
19#include <acro_config.h>
20#include <utilib/_math.h>
21#include <utilib/Uniform.h>
22#include <colin/BoundTypeArray.h>
23#include <scolib/DomainOpsArray.h>
24
25#define INT_ARRAY_MUTATION_UNIFORM  1
26#define INT_ARRAY_MUTATION_INTERVAL 2
27
28namespace scolib {
29
30using utilib::ParameterSet;
31
32template <class InfoT>
33class DomainOpsIntArray : public DomainOpsArray<int, InfoT>
34{
35public:
36
37  ///
38  typedef typename DomainOpsArray<int,InfoT>::info_t  info_t;
39
40  ///
41  typedef typename DomainOpsArray<int,InfoT>::point_t point_t;
42
43  ///
44  DomainOpsIntArray();
45
46  ///
47  void reset();
48
49  ///
50  template <class ProblemT>
51  void initialize(ProblemT& problem, unsigned int popsize_,double xover_rate, double m_rate)
52        {
53        DomainOpsArray<int,InfoT>::initialize( problem->num_int_vars(),
54                                                popsize_, xover_rate, m_rate);
55        if ((problem->num_int_vars() > 0) && (problem->enforcing_domain_bounds())) {
56           problem->get_int_bounds(lower,upper);
57           lbound_type.resize(lower.size());
58           ubound_type.resize(lower.size());
59           range.resize(lower.size());
60           for (unsigned int i=0; i<lower.size(); i++) {
61             lbound_type[i] = problem->int_lower_bound_type(i);
62             ubound_type[i] = problem->int_upper_bound_type(i);
63             range[i] = upper[i]-lower[i];
64             }
65           }
66        }
67
68  ///
69  void initialize_point(point_t& point, info_t& info)
70        { point.resize(lower.size()); }
71
72  ///
73  void randomize(point_t& point, InfoT& info)
74        {
75        for (unsigned int j=0; j<this->nvars; j++)
76          point[j] = utilib::Discretize(this->rnd(),lower[j],upper[j]);
77        }
78
79  ///
80  point_t lower;
81
82  ///
83  point_t upper;
84
85  ///
86  point_t range;
87
88  ///
89  colin::BoundTypeArray lbound_type;
90
91  ///
92  colin::BoundTypeArray ubound_type;
93
94protected:
95
96  ///
97  int mutation_range;
98
99  ///
100  void mutate_value(int i, int& val, info_t& info);
101
102};
103
104
105
106template <class InfoT>
107DomainOpsIntArray<InfoT>::DomainOpsIntArray()
108{
109this->crossover_blocksize=1;
110ParameterSet::create_categorized_parameter("intarray_xover_blocksize",
111        this->crossover_blocksize,
112        "<int>","1",
113        "Block size used with array-based two-point and uniform crossover",
114        "Crossover");
115
116this->crossover_str="twopoint";
117ParameterSet::create_categorized_parameter("intarray_xover_type",
118        this->crossover_str,
119        "<string>","twopoint",
120        "Crossover type\n\
121\t  onepoint      - standard one-point mutation\n\
122\t  twopoint      - standard two-point mutation\n\
123\t  uniform       - standard uniform mutation",
124        "Crossover");
125
126this->mutation_str = "uniform";
127ParameterSet::create_categorized_parameter("intarray_mutation_type",
128        this->mutation_str,
129        "<string>","uniform",
130        "Integer mutation type\n\
131\t  uniform  - replace the value with a uniformly random variable\n\
132\t  interval - replace the value with a uniform value in a local interval",
133        "Mutation");
134
135this->mutation_range=1;
136ParameterSet::create_categorized_parameter("intarray_mutation_range",
137        this->mutation_range,
138        "<int>","1",
139        "Range of mutation used for 'interval' mutation",
140        "Mutation");
141
142this->mutate_independently=false;
143ParameterSet::create_categorized_parameter("intarray_mutate_independently",
144        this->mutate_independently,
145        "<bool>","false",
146        "If true, then only mutate a single dimension.  Note that if this\n\
147\tvalue is true, then a single dimension is always mutated, so the\n\
148\tmutation allele rate is ignored.",
149        "Mutation");
150
151this->mutation_allele_rate=1.0;
152ParameterSet::create_categorized_parameter("intarray_mutation_allele_rate",
153        this->mutation_allele_rate,
154        "<double>","1.0",
155        "The probability that any given dimension of the intarray is mutated\n\tgiven that the individual is mutated",
156        "Mutation");
157}
158
159
160
161template <class InfoT>
162void DomainOpsIntArray<InfoT>::reset()
163{
164DomainOpsArray<int,InfoT>::reset();
165
166if ((this->mutation_str == "uniform") || (this->mutation_str == "offset_uniform")) {
167   this->mutation_type = INT_ARRAY_MUTATION_UNIFORM;
168   this->mutation_allele_rate =
169      (this->mutation_allele_rate < 0.0 ? std::sqrt(M_E/(double)this->nvars)/(double)this->popsize :
170        this->mutation_allele_rate);
171   }
172
173else if ((this->mutation_str == "interval") || (this->mutation_str == "replace_uniform")) {
174   this->mutation_type = INT_ARRAY_MUTATION_INTERVAL;
175   this->mutation_allele_rate =
176      (this->mutation_allele_rate < 0.0 ? std::sqrt(M_E/(double)this->nvars)/(double)this->popsize :
177        this->mutation_allele_rate);
178   }
179
180else
181   EXCEPTION_MNGR(std::runtime_error,"DomainOpsIntArray::reset - bad mutation type: \"" << this->mutation_str << "\".\n\t\tValid types are uniform and interval\n");
182
183if (this->crossover_str == "none")
184   this->crossover_type = ARRAY_XOVER_NONE;
185else if (this->crossover_str == "twopoint")
186   this->crossover_type = ARRAY_XOVER_TWOPOINT;
187else if (this->crossover_str == "uniform")
188   this->crossover_type = ARRAY_XOVER_UNIFORM;
189else
190   EXCEPTION_MNGR(std::runtime_error, "DomainOpsIntArray::reset -- bad xover type: \"" << this->crossover_str << "\".\n\t\tValid types are twopoint and uniform\n");
191}
192
193
194template <class InfoT>
195void DomainOpsIntArray<InfoT>::mutate_value(int i, int& value, info_t& info)
196{
197switch (this->mutation_type) {
198  case INT_ARRAY_MUTATION_INTERVAL:
199                value = utilib::Discretize(this->rnd(),lower[i],upper[i]);
200                break;
201
202  case INT_ARRAY_MUTATION_UNIFORM:
203                int tmp = utilib::Discretize(this->rnd(),
204                                        std::max(lower[i],value-mutation_range),
205                                        std::min(upper[i]-1,value+mutation_range-1));
206                value = (tmp < value ? tmp : tmp+1);
207                break;
208  };
209if (value > upper[i]) {
210   if (ubound_type[i] == colin::hard_bound) value = upper[i];
211   else if (ubound_type[i] == colin::periodic_bound)
212     while (value > upper[i]) value -= range[i];
213   }
214if (value < lower[i]) {
215   if (lbound_type[i] == colin::hard_bound) value = lower[i];
216   else if (lbound_type[i] == colin::periodic_bound)
217     while (value < lower[i]) value += range[i];
218   }
219}
220
221}
222
223#endif
Note: See TracBrowser for help on using the repository browser.