Interface FitnessEvaluator<T extends Comparable<T>>
- Type Parameters:
T
- the type of fitness values produced, must be comparable for selection operations
- All Known Implementing Classes:
FitnessEvaluatorBulkAsync
,FitnessEvaluatorSync
,GPUFitnessEvaluator
FitnessEvaluator provides a unified interface for computing fitness values regardless of the underlying evaluation mechanism. This abstraction allows the evolutionary algorithm to work with various evaluation strategies including synchronous, asynchronous, parallel, and distributed evaluation approaches.
The evaluator supports different execution models:
- Synchronous evaluation: Sequential evaluation of individuals
- Parallel evaluation: Concurrent evaluation using thread pools
- Asynchronous evaluation: Non-blocking evaluation with future-based results
- Distributed evaluation: Evaluation across multiple machines or processes
- Cached evaluation: Memoized results for previously evaluated genotypes
Key responsibilities include:
- Fitness computation: Converting genotypes into comparable fitness values
- Resource management: Handling computational resources and external dependencies
- Performance optimization: Efficient evaluation strategies for large populations
- Error handling: Managing evaluation failures and providing fallback mechanisms
Lifecycle methods provide hooks for:
- Setup: Initialize resources before evaluation begins
- Cleanup: Release resources after evaluation completes
- Batch processing: Optimize evaluation of entire populations
Common implementation patterns:
- Wrapper pattern: Adapting
Fitness
functions - Decorator pattern: Adding caching, logging, or monitoring capabilities
- Strategy pattern: Switching between different evaluation approaches
- Template method: Providing common evaluation infrastructure
Example implementations:
// Simple synchronous evaluator
FitnessEvaluator<Double> syncEvaluator = (generation, genotypes) -> {
return genotypes.stream()
.map(genotype -> computeFitness(genotype))
.collect(toList());
};
// Parallel evaluator with thread pool
FitnessEvaluator<Double> parallelEvaluator = (generation, genotypes) -> {
return genotypes.parallelStream()
.map(genotype -> computeFitness(genotype))
.collect(toList());
};
// Cached evaluator for expensive fitness functions
FitnessEvaluator<Double> cachedEvaluator = new CachedFitnessEvaluator<>(
baseFitnessFunction,
maxCacheSize: 10000
);
Performance considerations:
- Evaluation cost: Balance accuracy with computational efficiency
- Parallelization: Utilize multiple cores for independent evaluations
- Memory usage: Manage memory for large populations and complex fitness functions
- External resources: Handle databases, web services, or file system access efficiently
- See Also:
-
Method Summary
Modifier and TypeMethodDescriptionEvaluates the fitness of all genotypes in the given population.default void
Called after fitness evaluation completes for a generation.default void
Called before fitness evaluation begins for a generation.
-
Method Details
-
preEvaluation
default void preEvaluation()Called before fitness evaluation begins for a generation.This lifecycle method allows implementations to perform setup operations such as initializing resources, establishing connections, or preparing computational environments before the evaluation process starts.
Common setup activities include:
- Starting thread pools or worker processes
- Establishing database or network connections
- Loading configuration or reference data
- Initializing caches or temporary storage
The default implementation does nothing, making this method optional for implementations that don't require setup.
- Throws:
RuntimeException
- if setup fails and evaluation cannot proceed
-
postEvaluation
default void postEvaluation()Called after fitness evaluation completes for a generation.This lifecycle method allows implementations to perform cleanup operations such as releasing resources, closing connections, or persisting results after the evaluation process completes.
Common cleanup activities include:
- Shutting down thread pools or worker processes
- Closing database or network connections
- Flushing caches or saving state
- Logging performance metrics or statistics
The default implementation does nothing, making this method optional for implementations that don't require cleanup.
- Throws:
RuntimeException
- if cleanup fails (should not prevent evolution from continuing)
-
evaluate
Evaluates the fitness of all genotypes in the given population.This is the core method that computes fitness values for an entire population of genotypes. The implementation strategy (synchronous, parallel, asynchronous) is determined by the specific evaluator implementation.
Requirements:
- Return fitness values in the same order as input genotypes
- Return exactly one fitness value per input genotype
- Ensure fitness values are comparable for selection operations
- Handle empty populations gracefully (return empty list)
The generation parameter can be used for:
- Adaptive fitness functions that change over time
- Logging and monitoring evaluation progress
- Implementing generation-specific evaluation strategies
- Debugging and performance analysis
- Parameters:
generation
- the current generation number (0-based)genotypes
- the population of genotypes to evaluate- Returns:
- a list of fitness values corresponding to each genotype
- Throws:
IllegalArgumentException
- if genotypes list is nullRuntimeException
- if evaluation fails due to computational errors or resource issues
-