Source code for evokit.evolvables.prefabs

from evokit.core import Population
from evokit.evolvables.algorithms import SimpleLinearAlgorithm
from evokit.evolvables.selectors import TruncationSelector, Elitist
from evokit.evolvables.bitstring import BitString, CountBits, MutateBits
from evokit.tools.lineage import TrackParents
from evokit._utils.inspect import get_default_value
from typing import TYPE_CHECKING
from typing import Optional

if TYPE_CHECKING:
    from concurrent.futures import ProcessPoolExecutor


"""So, this global variable, ahh... fetches the default value
of :arg:`max_parents` in TrackParents's constructor. Because
apparently Python lets you do that.

So I'm doing something that I'm not really supposed to, and
making it a function so that I can do it again.
"""
_TRACK_PARENTS_MAX_PARENTS_DEFAULT: int =\
    get_default_value(TrackParents, "max_parents")

_MUTATEBITS_PROCESSES_DEFAULT: "Optional[int | ProcessPoolExecutor]" =\
    get_default_value(MutateBits.__init__, "processes")

_COUNTBITS_PROCESSES_DEFAULT: "Optional[int | ProcessPoolExecutor]" =\
    get_default_value(CountBits.__init__, "processes")


[docs] def make_onemax(pop_size: int, ind_size: int, mutate_p: float, variator_processes: "Optional[int | ProcessPoolExecutor]" = _MUTATEBITS_PROCESSES_DEFAULT, evaluator_processes: "Optional[int | ProcessPoolExecutor]" = _COUNTBITS_PROCESSES_DEFAULT, max_parents=_TRACK_PARENTS_MAX_PARENTS_DEFAULT)\ -> SimpleLinearAlgorithm[BitString]: """Create a simple elitist onemax algorithm that tracks 5 generations of parents. Useful for playing around with features. """ pop: Population[BitString] = Population( BitString.random(ind_size) for _ in range(pop_size)) return SimpleLinearAlgorithm(population=pop, variator=TrackParents( MutateBits( mutate_p, processes=variator_processes), max_parents=max_parents), evaluator=CountBits( processes=evaluator_processes), selector=Elitist( TruncationSelector(pop_size)))