|
3 | 3 |
|
4 | 4 | import numpy as np |
5 | 5 | import pandas as pd |
6 | | - |
7 | | -from scipy.optimize import differential_evolution, minimize_scalar |
8 | | - |
9 | 6 | from pymoo.core.problem import ElementwiseProblem |
10 | | -from pymoo.core.variable import Integer, Real, Choice, Binary |
| 7 | +from pymoo.core.variable import Binary, Choice, Integer, Real |
| 8 | +from scipy.optimize import differential_evolution, minimize_scalar, minimize |
11 | 9 |
|
12 | 10 | from corrai.base.math import METHODS |
13 | 11 | from corrai.base.model import Model |
| 12 | +from corrai.base.parameter import Parameter |
14 | 13 | from corrai.base.utils import check_indicators_configs |
15 | 14 | from corrai.sampling import Sample, SampleMethodsMixin |
16 | | -from corrai.base.parameter import Parameter |
17 | 15 |
|
18 | 16 |
|
19 | 17 | def check_duplicate_params(params: list["Parameter"]) -> None: |
@@ -724,6 +722,117 @@ def scalar_minimize( |
724 | 722 | options=options, |
725 | 723 | ) |
726 | 724 |
|
| 725 | + def minimize( |
| 726 | + self, |
| 727 | + indicator_config: str |
| 728 | + | tuple[str, str | Callable] |
| 729 | + | tuple[str, str | Callable, pd.Series], |
| 730 | + simulation_options: dict = None, |
| 731 | + simulation_kwargs=None, |
| 732 | + x0: list[float] = None, |
| 733 | + method=None, |
| 734 | + jac=None, |
| 735 | + hess=None, |
| 736 | + hessp=None, |
| 737 | + bounds=None, |
| 738 | + constraints=(), |
| 739 | + tol=None, |
| 740 | + callback=None, |
| 741 | + options=None, |
| 742 | + ): |
| 743 | + """ |
| 744 | + This method wraps `scipy.optimize.minimize` |
| 745 | +
|
| 746 | + Parameters |
| 747 | + ---------- |
| 748 | + indicator_config : str or tuple |
| 749 | + Indicator configuration passed to `ModelEvaluator.scipy_obj_function`: |
| 750 | + - If the model is **static**: a string representing the indicator name. |
| 751 | + - If the model is **dynamic**: a tuple of the form |
| 752 | + (indicator, func) or (indicator, func, reference) where: |
| 753 | + * indicator : str |
| 754 | + Indicator name in the simulation results. |
| 755 | + * func : str or Callable |
| 756 | + Aggregation function (method name registered in `METHODS` |
| 757 | + or a Python callable). |
| 758 | + * reference : optional |
| 759 | + Reference time series if the aggregation function is an |
| 760 | + error metric such as nmbe, cv_rmse, or mean_squared_error. |
| 761 | +
|
| 762 | + simulation_options : dict, optional |
| 763 | + Options for the simulation (e.g., stop time, solver settings). |
| 764 | +
|
| 765 | + simulation_kwargs : dict, optional |
| 766 | + Additional keyword arguments for simulation. |
| 767 | +
|
| 768 | + x0 : list of float, optional |
| 769 | + Initial guess for the optimization variables. |
| 770 | + If None, the initial values are set to the mean of each |
| 771 | + parameter interval. |
| 772 | +
|
| 773 | + method : str or callable, optional |
| 774 | + Optimization method to use (e.g., 'BFGS', 'L-BFGS-B', 'SLSQP'). |
| 775 | + Passed directly to `scipy.optimize.minimize`. |
| 776 | +
|
| 777 | + jac : callable or bool, optional |
| 778 | + Function computing the gradient of the objective, or a boolean |
| 779 | + indicating whether the objective returns the gradient. |
| 780 | +
|
| 781 | + hess : callable, optional |
| 782 | + Function computing the Hessian matrix of the objective. |
| 783 | +
|
| 784 | + hessp : callable, optional |
| 785 | + Function computing the Hessian-vector product. |
| 786 | +
|
| 787 | + bounds : sequence, optional |
| 788 | + Bounds on variables for bounded optimization methods. |
| 789 | +
|
| 790 | + constraints : sequence, optional |
| 791 | + Constraints definition for constrained optimization. |
| 792 | +
|
| 793 | + tol : float, optional |
| 794 | + Tolerance for convergence. |
| 795 | +
|
| 796 | + callback : callable, optional |
| 797 | + Function called after each iteration. |
| 798 | +
|
| 799 | + options : dict, optional |
| 800 | + Additional solver-specific options. |
| 801 | +
|
| 802 | + Returns |
| 803 | + ------- |
| 804 | + scipy.optimize.OptimizeResult |
| 805 | + Result of the optimization. Accessible also via the `result` |
| 806 | + attribute. |
| 807 | +
|
| 808 | + Notes |
| 809 | + ----- |
| 810 | + This method relies on `scipy.optimize.minimize`, which implements |
| 811 | + gradient-based and derivative-free local optimization algorithms. |
| 812 | + It is best suited for smooth problems and may converge to a local |
| 813 | + minimum depending on the initial guess. |
| 814 | +
|
| 815 | + For global optimization, consider using `diff_evo_minimize`. |
| 816 | + """ |
| 817 | + |
| 818 | + if x0 is None: |
| 819 | + x0 = [float(np.mean(par.interval)) for par in self.parameters] |
| 820 | + |
| 821 | + return minimize( |
| 822 | + self.model_evaluator.scipy_obj_function, |
| 823 | + x0, |
| 824 | + args=(indicator_config, simulation_options, simulation_kwargs), |
| 825 | + method=method, |
| 826 | + jac=jac, |
| 827 | + hess=hess, |
| 828 | + hessp=hessp, |
| 829 | + bounds=bounds, |
| 830 | + constraints=constraints, |
| 831 | + tol=tol, |
| 832 | + callback=callback, |
| 833 | + options=options, |
| 834 | + ) |
| 835 | + |
727 | 836 | def diff_evo_minimize( |
728 | 837 | self, |
729 | 838 | indicator_config: str |
|
0 commit comments