from spotoptim import SpotOptim
from spotoptim.surrogate import MLPSurrogate
from spotoptim.function.so import rosenbrock, ackley, robot_arm_hard
import numpy as np
def run_spotoptim_comparison(func, dim, bounds, max_iter=50):
print(f"\n--- optimizing {func.__name__} ({dim}D) ---")
# Define bounds list
bounds_list = [bounds] * dim
# 1. Default Surrogate (Kriging)
print("Running with Default Surrogate (Kriging)...")
opt_kriging = SpotOptim(
fun=func,
bounds=bounds_list,
max_iter=max_iter,
n_initial=10,
seed=42,
verbose=False
)
res_kriging = opt_kriging.optimize()
# 2. MLP Surrogate
print("Running with MLPSurrogate...")
# Use fewer epochs for speed in this demo, but enough to learn
# Note: MLPSurrogate improved with standard defaults (128x3 relu)
mlp = MLPSurrogate(epochs=200, verbose=False, seed=42)
opt_mlp = SpotOptim(
fun=func,
bounds=bounds_list,
surrogate=mlp,
max_iter=max_iter,
n_initial=10,
seed=42,
verbose=False
)
res_mlp = opt_mlp.optimize()
return {
"Function": func.__name__,
"Dim": dim,
"Best_Kriging": res_kriging.fun,
"Best_MLP": res_mlp.fun
}
# Scenarios
scenarios_opt = [
(rosenbrock, 2, (-5, 5)),
(rosenbrock, 10, (-5, 5)),
(ackley, 2, (-32.768, 32.768)),
(ackley, 10, (-32.768, 32.768)),
(robot_arm_hard, 10, (0.0, 1.0))
]
results_opt = []
print(f"\n{'Function':<15} | {'Dim':<5} | {'Best y (Default)':<20} | {'Best y (MLP)':<20}")
print("-" * 70)
for func, dim, bnds in scenarios_opt:
res = run_spotoptim_comparison(func, dim, bnds, max_iter=50)
results_opt.append(res)
print(f"{res['Function']:<15} | {res['Dim']:<5} | {res['Best_Kriging']:<20.6e} | {res['Best_MLP']:<20.6e}")