Source code for lightwin.optimisation.algorithms.simulated_annealing

"""Define the simulated annealing algorithm."""

from typing import Any

from scipy.optimize import OptimizeResult, dual_annealing

from lightwin.optimisation.algorithms.algorithm import (
    OptimisationAlgorithm,
    OptiSol,
)


[docs] class SimulatedAnnealing(OptimisationAlgorithm): """Simulated Annealing method for global optimization.""" supports_constraints = False
[docs] def optimize(self) -> OptiSol: """Set up and run the simulated annealing algorithm. Returns ------- Contains solution(s), objective value(s), status, etc. """ bounds = self._format_bounds() result = dual_annealing( func=self._norm_wrapper_residuals, bounds=bounds, **self.optimisation_algorithm_kwargs, ) self.opti_sol = self._generate_opti_sol(result) self._finalize(self.opti_sol) return self.opti_sol
@property def _default_kwargs(self) -> dict[str, Any]: """Default parameters for dual_annealing.""" kwargs = { "maxiter": 100, "initial_temp": 5230.0, "restart_temp_ratio": 2e-5, "visit": 2.62, "accept": -5.0, "no_local_search": False, } return kwargs
[docs] def _generate_opti_sol(self, result: OptimizeResult) -> OptiSol: """Package the results into an OptiSol dictionary.""" cavity_settings = self._create_set_of_cavity_settings(result.x) opti_sol: OptiSol = { "var": result.x, "cavity_settings": cavity_settings, "fun": result.fun, "objectives": self._get_objective_values(result.x), "success": result.success, "info": result.message.insert(0, "SimulatedAnnealing:"), } return opti_sol
[docs] def _format_bounds(self) -> list[tuple[float, float]]: """Convert Variable objects to a list of bounds.""" return [var.limits for var in self._variables]