use genetic_rs::prelude::*;
#[derive(Clone, Debug, PartialEq)]
struct MyGenome {
val: f32,
}
impl RandomlyMutable for MyGenome {
type Context = ();
fn mutate(&mut self, _: &(), rate: f32, rng: &mut impl Rng) {
self.val += rng.random::<f32>() * rate;
}
}
impl Crossover for MyGenome {
type Context = ();
fn crossover(&self, other: &Self, _: &(), rate: f32, rng: &mut impl Rng) -> Self {
let mut child = Self {
val: (self.val + other.val) / 2.,
};
child.mutate(&(), rate, rng);
child
}
}
impl GenerateRandom for MyGenome {
fn gen_random(rng: &mut impl Rng) -> Self {
Self {
val: rng.random::<f32>() * 1000.,
}
}
}
fn main() {
let mut rng = rand::rng();
let magic_number = rng.random::<f32>() * 1000.;
let fitness = move |e: &MyGenome| -> f32 { 1.0 / (magic_number - e.val).abs().max(1e-7) };
let mut sim = GeneticSim::new(
Vec::gen_random(&mut rng, 100),
FitnessEliminator::new_without_observer(fitness),
CrossoverRepopulator::new(0.25, ()), );
sim.perform_generations(100);
dbg!(sim.genomes, magic_number);
}