13#if !defined(ULTRA_EVOLUTION_STRATEGY_H)
14# error "Don't include this file directly, include the specific .h instead"
17#if !defined(ULTRA_EVOLUTION_STRATEGY_TCC)
18#define ULTRA_EVOLUTION_STRATEGY_TCC
35evolution_strategy<E>::evolution_strategy(
const problem &prob, E &eva)
36 : eva_(eva), prob_(prob)
41template<LayeredPopulation P>
42bool evolution_strategy<E>::valid_layer(P &pop,
typename P::layer_iter iter)
44 return pop.layers() && iterator_of(iter, pop.range_of_layers());
117template<Population P>
125 assert(&pop.problem() == &this->get_problem());
126 const auto ¶ms(pop.problem().params);
127 assert(params.evolution.max_stuck_gen);
129 for (
const auto layers(pop.range_of_layers());
auto &layer : layers)
130 if (sum.stagnation() > params.evolution.max_stuck_gen
131 && issmall(sum.az.fit_dist(layer).variance()))
133 layer.reset(pop.problem());
134 ultraINFO(
"Resetting layer {}", layer.uid());
153 select_(this->eva_, prob.params),
154 recombine_(this->eva_, prob),
155 replace_(this->eva_, prob.params)
181template<LayeredPopulation P>
183 P &pop,
typename P::layer_iter iter,
186 Expects(this->valid_layer(pop, iter));
192 status = starting_status]
mutable
194 Ensures(sel_pop.size());
195 Ensures(rep_pop.size());
196 Ensures(&sel_pop.primary() == &rep_pop.primary());
198 const auto parents(this->select_(sel_pop));
199 const auto offspring(this->recombine_(parents));
200 this->replace_(rep_pop, offspring, status);
213template<LayeredPopulation P>
232template<LayeredPopulation P>
235 return pop.layers() < 3 ? nullptr : &pop.back();
249template<LayeredPopulation P>
252 return hardware_threads();
272template<LayeredPopulation P>
276 Expects(&pop.problem() == &this->get_problem());
278 const auto ¶ms(pop.problem().params);
279 Expects(params.alps.max_layers > 1);
283 const auto layers(pop.range_of_layers());
284 bool layer_structure_changed(
false);
286 if (pop.layers() > 1)
288 auto layer(std::next(layers.begin()));
290 while (layer != layers.end())
292 if (almost_equal(sum.az.fit_dist(*std::prev(layer)).mean(),
293 sum.az.fit_dist(*layer).mean()))
295 ultraDEBUG(
"ALPS: erasing layer UID={}", layer->uid());
296 layer = pop.erase(layer);
297 layer_structure_changed =
true;
301 const auto sd(sum.az.fit_dist(*layer).standard_deviation());
302 const bool converged(issmall(sd));
306 const auto prev_allowed(layer->allowed());
307 const auto new_allowed(std::max(params.population.min_individuals,
310 if (new_allowed < prev_allowed)
312 ultraDEBUG(
"ALPS: decreasing allowed individuals of layer "
313 "UID={} to {}", layer->uid(), new_allowed);
315 layer->allowed(new_allowed);
318 else if (layer->allowed() < params.population.individuals)
320 ultraDEBUG(
"ALPS: restoring allowed individuals of layer UID={} "
321 "to {}", layer->uid(), params.population.individuals);
323 layer->allowed(params.population.individuals);
332 if (sum.generation && sum.generation % params.alps.age_gap == 0)
334 if (pop.layers() < params.alps.max_layers)
336 ultraDEBUG(
"ALPS: adding layer");
338 layer_structure_changed =
true;
342 ultraDEBUG(
"ALPS: try moving up first layer");
343 this->replace_.try_promote_individuals(pop.front(), pop.layer(1));
344 pop.init(pop.front());
348 if (layer_structure_changed)
369 std::max<unsigned>(2, std::thread::hardware_concurrency());
376std_es<E>::std_es(
const problem &prob, E &eva)
377 : evolution_strategy<E>(prob, eva),
378 select_(this->eva_, prob.params),
379 recombine_(this->eva_, prob),
380 replace_(this->eva_, prob.params)
399template<SizedRandomAccessPopulation P>
405 [
this, &p = pop, status = starting_status]()
mutable
409 const auto parents(this->select_(p));
410 const auto offspring(this->recombine_(parents));
411 this->replace_(p, offspring, status);
430template<LayeredPopulation P>
432 [[maybe_unused]] P &pop,
typename P::layer_iter iter,
435 Expects(this->valid_layer(pop, iter));
441de_es<E>::de_es(
const problem &prob, E &eva)
444 replace_(this->eva_, prob.params)
463template<SizedRandomAccessPopulation P>
465 [[maybe_unused]] P &pop,
469 [
this, &p = pop, status = starting_status]()
mutable
473 const auto selected(this->select_(p));
474 const auto offspring(this->recombine_(selected));
475 this->replace_(selected.target, offspring, status);
494template<LayeredPopulation P>
496 [[maybe_unused]] P &pop,
typename P::layer_iter iter,
499 Expects(this->valid_layer(pop, iter));
alps_layer_pair< typename P::layer_t > replacement_layers(P &pop, typename P::layer_iter l)
Definition alps.h:220
alps_layer_pair< const typename P::layer_t > selection_layers(const P &pop, typename P::layer_const_iter l)
Definition alps.h:257
alps_es(const problem &, E &)
Definition evolution_strategy.h:152
void after_generation(P &, const summary< individual_t, fitness_t > &)
Definition evolution_strategy.h:274
void init(P &) const
Definition evolution_strategy.h:215
auto * refinement_subgroup(P &) const noexcept
Definition evolution_strategy.h:234
auto operations(P &, typename P::layer_iter, const evolution_status< individual_t, fitness_t > &) const
Definition evolution_strategy.h:183
std::size_t max_parallelism(const P &) const noexcept
Definition evolution_strategy.h:251
static parameters shape(parameters)
Definition evolution_strategy.h:366
auto operations(P &, const evolution_status< individual_t, fitness_t > &) const
Definition evolution_strategy.h:465
Definition evolution_status.h:36
Definition evolution_strategy.h:66
std::size_t max_parallelism(const P &) const noexcept
Definition evolution_strategy.h:85
P * refinement_subgroup(P &) const noexcept
Definition evolution_strategy.h:67
void after_generation(P &, const summary< individual_t, fitness_t > &)
Definition evolution_strategy.h:119
auto operations(P &, const evolution_status< individual_t, fitness_t > &) const
Definition evolution_strategy.h:401
Definition evolution_summary.h:33
Definition population.h:42
double p_main_layer
Definition alps.h:178
std::size_t max_layers
Maximum number of layers an ALPS layered population can grow to.
Definition alps.h:172
unsigned age_gap
Definition alps.h:169
Definition parameters.h:26