ChromosomeFactoryProvider.java
package net.bmahe.genetics4j.core.chromosomes.factory;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Objects;
import java.util.function.Function;
import java.util.random.RandomGenerator;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.immutables.value.Value;
import net.bmahe.genetics4j.core.chromosomes.Chromosome;
import net.bmahe.genetics4j.core.spec.chromosome.ChromosomeSpec;
@Value.Immutable
public abstract class ChromosomeFactoryProvider {
final static public Logger logger = LogManager.getLogger(ChromosomeFactoryProvider.class);
public abstract RandomGenerator randomGenerator();
@Value.Default
public List<ChromosomeFactory<? extends Chromosome>> defaultChromosomeFactories() {
final var randomGenerator = randomGenerator();
return Arrays.asList(new BitChromosomeFactory(randomGenerator),
new IntChromosomeFactory(randomGenerator),
new DoubleChromosomeFactory(randomGenerator),
new FloatChromosomeFactory(randomGenerator));
}
public abstract List<Function<ChromosomeFactoryProvider, ChromosomeFactory<? extends Chromosome>>> chromosomeFactoriesGenerator();
@Value.Derived
public List<ChromosomeFactory<? extends Chromosome>> chromosomeFactories() {
final List<ChromosomeFactory<? extends Chromosome>> chromosomeFactories = new ArrayList<>();
final List<ChromosomeFactory<? extends Chromosome>> defaultChromosomeFactories = defaultChromosomeFactories();
if (defaultChromosomeFactories.isEmpty() == false) {
chromosomeFactories.addAll(defaultChromosomeFactories);
}
chromosomeFactoriesGenerator().stream()
.map(generator -> generator.apply(this))
.forEach(cf -> chromosomeFactories.add(cf));
return chromosomeFactories;
}
public ChromosomeFactory<? extends Chromosome> provideChromosomeFactory(final ChromosomeSpec chromosomeSpec) {
Objects.requireNonNull(chromosomeSpec);
final List<ChromosomeFactory<? extends Chromosome>> chromosomeFactories = chromosomeFactories();
logger.trace("Known chromosome factories: {}", chromosomeFactories);
return chromosomeFactories.stream()
.dropWhile((chromosomeFactory) -> chromosomeFactory.canHandle(chromosomeSpec) == false)
.findFirst()
.orElseThrow(() -> new IllegalStateException(
"Could not find a chromosome factory for chromosome spec: " + chromosomeSpec));
}
public static ImmutableChromosomeFactoryProvider.Builder builder() {
return ImmutableChromosomeFactoryProvider.builder();
}
}