use crate::{
Chromosome, Codec, Gene, Genotype, PermutationChromosome, PermutationGene, random_provider,
};
use std::sync::Arc;
#[derive(Clone)]
pub struct PermutationCodec<A: PartialEq + Clone> {
alleles: Arc<[A]>,
}
impl<A: PartialEq + Clone> PermutationCodec<A> {
pub fn new(alleles: Vec<A>) -> Self {
PermutationCodec {
alleles: alleles.into_boxed_slice().into(),
}
}
}
impl<A: PartialEq + Clone> Codec<PermutationChromosome<A>, Vec<A>> for PermutationCodec<A> {
fn encode(&self) -> Genotype<PermutationChromosome<A>> {
Genotype::from(PermutationChromosome::new(
random_provider::shuffled_indices(0..self.alleles.len())
.iter()
.map(|i| PermutationGene::new(*i, Arc::clone(&self.alleles)))
.collect(),
Arc::clone(&self.alleles),
))
}
fn decode(&self, genotype: &Genotype<PermutationChromosome<A>>) -> Vec<A> {
genotype
.iter()
.flat_map(|chromosome| {
chromosome
.as_slice()
.iter()
.map(|gene| gene.allele().clone())
})
.collect()
}
}
impl<A: PartialEq + Clone> Codec<PermutationChromosome<A>, Vec<Vec<A>>>
for Vec<PermutationChromosome<A>>
{
fn encode(&self) -> Genotype<PermutationChromosome<A>> {
Genotype::from(
self.iter()
.map(|chromosome| {
PermutationChromosome::new(
chromosome
.as_slice()
.iter()
.map(|gene| gene.new_instance())
.collect(),
Arc::clone(chromosome.alleles()),
)
})
.collect::<Vec<PermutationChromosome<A>>>(),
)
}
fn decode(&self, genotype: &Genotype<PermutationChromosome<A>>) -> Vec<Vec<A>> {
genotype
.iter()
.map(|chromosome| {
chromosome
.as_slice()
.iter()
.map(|gene| gene.allele().clone())
.collect::<Vec<A>>()
})
.collect::<Vec<Vec<A>>>()
}
}
impl<A: PartialEq + Clone> Codec<PermutationChromosome<A>, Vec<A>> for PermutationChromosome<A> {
fn encode(&self) -> Genotype<PermutationChromosome<A>> {
Genotype::from(PermutationChromosome::new(
self.as_slice()
.iter()
.map(|gene| gene.new_instance())
.collect(),
Arc::clone(self.alleles()),
))
}
fn decode(&self, genotype: &Genotype<PermutationChromosome<A>>) -> Vec<A> {
genotype
.iter()
.flat_map(|chromosome| {
chromosome
.as_slice()
.iter()
.map(|gene| gene.allele().clone())
})
.collect()
}
}