Coverage for jetgp/hyperparameter_optimizers/powell.py: 88%
25 statements
« prev ^ index » next coverage.py v7.10.7, created at 2026-03-31 11:46 -0500
« prev ^ index » next coverage.py v7.10.7, created at 2026-03-31 11:46 -0500
1import numpy as np
2from scipy.optimize import minimize
4def powell(func, lb, ub, **kwargs):
5 """
6 Powell's method with bounds and multi-start.
8 Parameters
9 ----------
10 func : callable
11 Function to minimize.
12 lb, ub : array-like
13 Lower and upper bounds.
14 kwargs : dict
15 Optional arguments:
16 - x0 : initial guess for first restart
17 - n_restart_optimizer : number of random restarts (default=10)
18 - debug : bool, print intermediate results (default=False)
19 - Any Powell-specific options: maxiter, xtol, ftol, disp
20 """
21 x0 = kwargs.pop("x0", None)
22 n_restart_optimizer = kwargs.pop("n_restart_optimizer", 10)
23 debug = kwargs.pop("debug", False)
25 # Extract Powell-specific options
26 options = {}
27 for key in ["maxiter", "xtol", "ftol", "disp"]:
28 if key in kwargs:
29 options[key] = kwargs.pop(key)
31 lb = np.array(lb)
32 ub = np.array(ub)
33 best_x = None
34 best_val = np.inf
36 for i in range(n_restart_optimizer):
37 if x0 is not None and i == 0:
38 x_init = np.array(x0)
39 else:
40 x_init = np.random.uniform(lb, ub)
42 res = minimize(
43 func,
44 x_init,
45 method="Powell",
46 bounds=list(zip(lb, ub)),
47 options=options,
48 **kwargs # extra kwargs forwarded
49 )
51 if res.fun < best_val:
52 best_val = res.fun
53 best_x = res.x
55 if debug:
56 print(f"[Powell] Restart {i+1}/{n_restart_optimizer} -> best_val={best_val}")
58 return best_x, best_val