131 {
132
133 std::vector<Candidate> mirrorPopulation;
134 std::vector<Candidate> oldPopulation = population;
135
137
138 case QuantLib::DifferentialEvolution::Rand1Standard: {
139 randomize(population.begin(), population.end(),
rng_);
140 std::vector<Candidate> shuffledPop1 = population;
141 randomize(population.begin(), population.end(),
rng_);
142 std::vector<Candidate> shuffledPop2 = population;
143 randomize(population.begin(), population.end(),
rng_);
144 mirrorPopulation = shuffledPop1;
145
146 for (Size popIter = 0; popIter < population.size(); popIter++) {
147 population[popIter].values =
148 population[popIter].values +
149 configuration().stepsizeWeight * (shuffledPop1[popIter].values - shuffledPop2[popIter].values);
150 }
151 } break;
152
153 case QuantLib::DifferentialEvolution::BestMemberWithJitter: {
154 randomize(population.begin(), population.end(),
rng_);
155 std::vector<Candidate> shuffledPop1 = population;
156 randomize(population.begin(), population.end(),
rng_);
157 Array jitter(population[0].values.size(), 0.0);
158
159 for (Size popIter = 0; popIter < population.size(); popIter++) {
160 for (double& jitterIter : jitter) {
161 jitterIter =
rng_.nextReal();
162 }
163 population[popIter].values =
164 bestMemberEver_.values + (shuffledPop1[popIter].values - population[popIter].values) *
166 }
167 mirrorPopulation = std::vector<Candidate>(population.size(),
bestMemberEver_);
168 } break;
169
170 case QuantLib::DifferentialEvolution::CurrentToBest2Diffs: {
171 randomize(population.begin(), population.end(),
rng_);
172 std::vector<Candidate> shuffledPop1 = population;
173 randomize(population.begin(), population.end(),
rng_);
174
175 for (Size popIter = 0; popIter < population.size(); popIter++) {
176 population[popIter].values =
177 oldPopulation[popIter].values +
179 configuration().stepsizeWeight * (population[popIter].values - shuffledPop1[popIter].values);
180 }
181 mirrorPopulation = shuffledPop1;
182 } break;
183
184 case QuantLib::DifferentialEvolution::Rand1DiffWithPerVectorDither: {
185 randomize(population.begin(), population.end(),
rng_);
186 std::vector<Candidate> shuffledPop1 = population;
187 randomize(population.begin(), population.end(),
rng_);
188 std::vector<Candidate> shuffledPop2 = population;
189 randomize(population.begin(), population.end(),
rng_);
190 mirrorPopulation = shuffledPop1;
191 Array FWeight = Array(population.front().values.size(), 0.0);
192 for (double& fwIter : FWeight)
194 for (Size popIter = 0; popIter < population.size(); popIter++) {
195 population[popIter].values =
196 population[popIter].values + FWeight * (shuffledPop1[popIter].values - shuffledPop2[popIter].values);
197 }
198 } break;
199
200 case QuantLib::DifferentialEvolution::Rand1DiffWithDither: {
201 randomize(population.begin(), population.end(),
rng_);
202 std::vector<Candidate> shuffledPop1 = population;
203 randomize(population.begin(), population.end(),
rng_);
204 std::vector<Candidate> shuffledPop2 = population;
205 randomize(population.begin(), population.end(),
rng_);
206 mirrorPopulation = shuffledPop1;
208 for (Size popIter = 0; popIter < population.size(); popIter++) {
209 population[popIter].values =
210 population[popIter].values + FWeight * (shuffledPop1[popIter].values - shuffledPop2[popIter].values);
211 }
212 } break;
213
214 case QuantLib::DifferentialEvolution::EitherOrWithOptimalRecombination: {
215 randomize(population.begin(), population.end(),
rng_);
216 std::vector<Candidate> shuffledPop1 = population;
217 randomize(population.begin(), population.end(),
rng_);
218 std::vector<Candidate> shuffledPop2 = population;
219 randomize(population.begin(), population.end(),
rng_);
220 mirrorPopulation = shuffledPop1;
221 Real probFWeight = 0.5;
222 if (
rng_.nextReal() < probFWeight) {
223 for (Size popIter = 0; popIter < population.size(); popIter++) {
224 population[popIter].values =
225 oldPopulation[popIter].values +
226 configuration().stepsizeWeight * (shuffledPop1[popIter].values - shuffledPop2[popIter].values);
227 }
228 } else {
230 for (Size popIter = 0; popIter < population.size(); popIter++) {
231 population[popIter].values =
232 oldPopulation[popIter].values + K * (shuffledPop1[popIter].values - shuffledPop2[popIter].values -
233 2.0 * population[popIter].values);
234 }
235 }
236 } break;
237
238 case QuantLib::DifferentialEvolution::Rand1SelfadaptiveWithRotation: {
239 randomize(population.begin(), population.end(),
rng_);
240 std::vector<Candidate> shuffledPop1 = population;
241 randomize(population.begin(), population.end(),
rng_);
242 std::vector<Candidate> shuffledPop2 = population;
243 randomize(population.begin(), population.end(),
rng_);
244 mirrorPopulation = shuffledPop1;
245
247
248 for (Size popIter = 0; popIter < population.size(); popIter++) {
249 if (
rng_.nextReal() < 0.1) {
251 } else {
252 population[popIter].values =
254 currGenSizeWeights_[popIter] * (shuffledPop1[popIter].values - shuffledPop2[popIter].values);
255 }
256 }
257 } break;
258
259 default:
260 QL_FAIL(
"Unknown strategy (" << Integer(
configuration().strategy) <<
")");
261 }
262
263 crossover(oldPopulation, population, population, mirrorPopulation, p);
264}
void crossover(const std::vector< Candidate > &oldPopulation, std::vector< Candidate > &population, const std::vector< Candidate > &mutantPopulation, const std::vector< Candidate > &mirrorPopulation, Problem_MT &p) const
Array rotateArray(Array inputArray) const
void adaptSizeWeights() const