ECF 1.5
Mutation.cpp
1#include "ECF_base.h"
2
3const int RANDOM_GENOTYPE = 0;
4const int ALL_GENOTYPES = 1;
5
6
11{
12 return indMutProb_;
13}
14
15
19double Mutation::setIndMutProb(double newProb)
20{
21 if(newProb >= 0 && newProb <= 1)
22 indMutProb_ = newProb;
23 return indMutProb_;
24}
25
26
31{
32 state->getRegistry()->registerEntry("mutation.indprob", (voidP) new double(0.3), ECF::DOUBLE,
33 "individual mutation probability (unless the algorithm overrides it) (default: 0.3)");
34// state->getRegistry()->registerEntry("mutation.geneprob", (voidP) new double(0.01), ECF::DOUBLE);
35 state->getRegistry()->registerEntry("mutation.genotypes", (voidP) new std::string("random"), ECF::STRING,
36 "if there are multiple genotypes, which to mutate? 'random': a random one, all: mutate all (default: random)");
37 state->getRegistry()->registerEntry("mutation.protected", (voidP) new std::string(""), ECF::STRING,
38 "indexes of genotypes (separated by spaces) that are excluded (protected) from mutation (default: none)");
39}
40
41
45bool Mutation::initialize(StateP state)
46{
47 state_ = state;
48 protectedGenotypes_.clear();
49 protectedGenotypes_.insert(protectedGenotypes_.begin(), operators.size(), false);
50 opProb.clear();
51
52 voidP sptr = state->getRegistry()->getEntry("mutation.indprob");
53 indMutProb_ = *((double*)sptr.get());
54
55 sptr = state->getRegistry()->getEntry("mutation.geneprob");
56// geneMutProb_ = *((double*)sptr.get());
57// if(state->getRegistry()->isModified("mutation.geneprob") == false)
58// geneMutProb_ = 0;
59
60 sptr = state->getRegistry()->getEntry("mutation.genotypes");
61 std::string mutGen = *((std::string*)sptr.get());
62
63 mutateGenotypes_ = RANDOM_GENOTYPE;
64 if(mutGen == "random")
65 mutateGenotypes_ = RANDOM_GENOTYPE;
66 else if(mutGen == "all")
67 mutateGenotypes_ = ALL_GENOTYPES;
68 else
69 ECF_LOG_ERROR(state, "Warning: invalid parameter value (key: mutation.genotypes)");
70
71 // read protected genotypes
72 std::stringstream ss;
73 sptr = state->getRegistry()->getEntry("mutation.protected");
74 ss << *((std::string*) sptr.get());
75 uint genId;
76 while(ss >> genId) { // read all the data from string
77 if(genId >= protectedGenotypes_.size()) {
78 ECF_LOG_ERROR(state, "Error: invalid genotype index (key: mutation.protected)!");
79 throw("");
80 }
81 protectedGenotypes_[genId] = true;
82 }
83
84 // initialize operators for all genotypes
85 for(uint gen = 0; gen < operators.size(); gen++) {
86 uint nOps = (uint) operators[gen].size();
87 // if the genotype doesn't define mutation operators
88 if(nOps == 0) {
89 protectedGenotypes_[gen] = true;
90 std::vector<double> empty;
91 opProb.push_back(empty);
92 break;
93 }
94 for(uint i = 0; i < nOps; i++) {
95 operators[gen][i]->state_ = state;
96 operators[gen][i]->initialize(state);
97 }
98 // calculate cumulative operator probabilities
99 std::vector<double> probs(nOps);
100 probs[0] = operators[gen][0]->probability_;
101 for(uint i = 1; i < nOps; i++) {
102 probs[i] = probs[i - 1] + operators[gen][i]->probability_;
103 }
104 if(probs[nOps - 1] == 0) {
105 std::vector<double> none(1);
106 none[0] = -1;
107 opProb.push_back(none);
108 } else {
109 if(probs[nOps - 1] != 1) {
110 double normal = probs[nOps - 1];
111 ECF_LOG_ERROR(state, "Warning: " + operators[gen][0]->myGenotype_->getName() +
112 " mutation operators: cumulative probability not equal to 1 (sum = " + dbl2str(normal) + ")");
113 for(uint i = 0; i < probs.size(); i++)
114 probs[i] /= normal;
115 }
116 opProb.push_back(probs);
117 }
118 }
119 return true;
120}
121
122
133uint Mutation::mutation(const std::vector<IndividualP> &pool)
134{
135 uint mutated = 0;
136 for(uint i = 0; i < pool.size(); i++) {
137 if(state_->getRandomizer()->getRandomDouble() <= indMutProb_) {
138 mutated++;
139 mutate(pool[i]);
140 }
141 }
142
143 return mutated;
144}
145
146
153bool Mutation::mutate(IndividualP ind)
154{
155 ind->fitness->setInvalid();
156 // set mutation context
157 state_->getContext()->mutatedIndividual = ind;
158 ECF_LOG(state_, 5, "Mutating individual: " + ind->toString());
159 currentInd = ind;
160
161 // if mutating a random genotype
162 if(mutateGenotypes_ == RANDOM_GENOTYPE) {
163 uint iGenotype = state_->getRandomizer()->getRandomInteger((int)ind->size());
164 if(protectedGenotypes_[iGenotype])
165 return false;
166 // choose operator
167 uint iOperator;
168 if(opProb[iGenotype][0] < 0)
169 iOperator = state_->getRandomizer()->getRandomInteger((int)operators[iGenotype].size());
170 else {
171 double random = state_->getRandomizer()->getRandomDouble();
172 iOperator = 0;
173 while(opProb[iGenotype][iOperator] < random)
174 iOperator++;
175 }
176 operators[iGenotype][iOperator]->mutate(ind->at(iGenotype));
177 }
178
179 // if mutating all genotypes in the individual
180 else if(mutateGenotypes_ == ALL_GENOTYPES) {
181 for(uint iGenotype = 0; iGenotype < ind->size(); iGenotype++) {
182 if(protectedGenotypes_[iGenotype])
183 continue;
184 // choose operator
185 uint iOperator;
186 if(opProb[iGenotype][0] < 0)
187 iOperator = state_->getRandomizer()->getRandomInteger((int)operators[iGenotype].size());
188 else {
189 double random = state_->getRandomizer()->getRandomDouble();
190 iOperator = 0;
191 while(opProb[iGenotype][iOperator] < random)
192 iOperator++;
193 }
194 operators[iGenotype][0]->mutate(ind->at(iGenotype));
195 }
196 }
197
198 ECF_LOG(state_, 5, "Mutated individual: " + ind->toString());
199
200 return true;
201}
202
double getIndMutProb()
Return current individual mutation probability.
Definition: Mutation.cpp:10
double setIndMutProb(double)
Set new individual mutation probability (ignored if not [0, 1])
Definition: Mutation.cpp:19
uint mutateGenotypes_
what genotypes (if more than one) to mutate (random, all)
Definition: Mutation.h:72
std::vector< bool > protectedGenotypes_
protected (non-mutatable) genotypes flags
Definition: Mutation.h:73
bool initialize(StateP)
Initialize all mutation operators of all active genotypes.
Definition: Mutation.cpp:45
uint mutation(const std::vector< IndividualP > &)
Perform mutation on a pool of individuals.
Definition: Mutation.cpp:133
bool mutate(IndividualP ind)
Mutate an individual.
Definition: Mutation.cpp:153
double indMutProb_
mutation probability of an individual
Definition: Mutation.h:71
void registerParameters(StateP)
Register mutation related but Genotype unrelated parameters.
Definition: Mutation.cpp:30
std::vector< std::vector< double > > opProb
usage probabilities for each MutationOp operator
Definition: Mutation.h:65
std::vector< std::vector< MutationOpP > > operators
vectors of mutation operators for each genotype
Definition: Mutation.h:64