genetic_algorithms 3.0.0

Library for solving genetic algorithm problems
Documentation
//! Age-based survivor selection.
//!
//! Retains the youngest individuals (lowest age) after parents and offspring
//! have been merged. This strategy favours fresh genetic material and
//! prevents long-lived individuals from dominating the population.

pub(crate) use crate::traits::ChromosomeT;
#[cfg(all(not(target_arch = "wasm32"), feature = "parallel"))]
use rayon::prelude::*;

/// Age-based survivor selection: sorts individuals by age (youngest first)
/// and keeps the top `population_size`.
///
/// # Arguments
///
/// * `chromosomes` - Combined parents + offspring (modified in place).
/// * `population_size` - Desired population size after selection.
///
/// # Examples
///
/// ```rust,no_run
/// use genetic_algorithms::operations::survivor::age_based;
/// use genetic_algorithms::chromosomes::Binary;
/// let mut population: Vec<Binary> = vec![Binary::new(); 20];
/// age_based(&mut population, 10);
/// ```
pub fn age_based<U: ChromosomeT>(chromosomes: &mut Vec<U>, population_size: usize) {
    //We first sort the chromosomes by their fitness
    crate::log_debug!(target="survivor_events", method="age_based"; "Starting age based survivor method");
    #[cfg(all(not(target_arch = "wasm32"), feature = "parallel"))]
    chromosomes.par_sort_unstable_by(|a, b| a.age().cmp(&b.age()));
    #[cfg(any(target_arch = "wasm32", not(feature = "parallel")))]
    chromosomes.sort_unstable_by(|a, b| a.age().cmp(&b.age()));

    // Drop surplus individuals from the tail in O(1) instead of
    // loop of Vec::remove (O(N) per removal).
    crate::log_trace!(target="survivor_events", method="age_based"; "Chromosomes length {} - population size {}", chromosomes.len(), population_size);
    if chromosomes.len() > population_size {
        chromosomes.truncate(population_size);
    }
    crate::log_debug!(target="survivor_events", method="age_based"; "Age based survivor method finished");
}