scipy.optimize.differential_evolution 是最省事的全局优化方法,收敛稳、自动处理边界、对非凸/噪声函数鲁棒;需注意目标函数返回标量、bounds为tuple列表、防nan/inf、避免目标函数中print等细节。

用 scipy.optimize.differential_evolution 做全局优化最省事
绝大多数场景下,别自己手写遗传算法——differential_evolution 是 SciPy 内置的进化策略实现,收敛稳、接口干净、自动处理边界,比手动调 deap 或 pygad 少踩 80% 的坑。
它本质是带变异-交叉-选择的实数编码进化算法,不依赖种群初始化质量,对非凸、非连续、带噪声的目标函数鲁棒性强。
- 目标函数必须返回标量(
float),且参数为一维numpy.ndarray,例如def obj(x): return x[0]**2 + x[1]**2 -
bounds必须是listoftuple,如[(-5, 5), (0, 10)],不能传np.array或单个tuple - 默认种群大小是
popsize=15× 参数维数,高维问题(>20 维)建议显式设popsize=20防早熟 - 遇到
RuntimeWarning: invalid value encountered in double_scalars,大概率是目标函数在某次评估中返回了nan或inf,加一行if np.any(np.isnan(x)) or np.any(np.isinf(x)): return np.inf拦住
deap 手写 GA 时,适应度值必须是 tuple
哪怕你只优化一个目标,deap 强制要求 fitness.values 是元组,写成 (score,) 而不是 score。漏掉逗号会报错 TypeError: 'float' object is not iterable,这个错误信息完全不提示真实原因。
- 注册评估函数时,确保返回
tuple:toolbox.register("evaluate", lambda ind: (obj_func(ind),)) - 用
tools.initRepeat初始化种群,别用list(map(...)),否则后续varAnd可能出错 - 如果目标函数计算开销大,务必用
tools.selTournament替代selRoulette,轮盘赌在适应度差异大时容易退化成“只选最优个体” -
cxBlend和mutGaussian对边界敏感:若个体超出bounds,不会自动裁剪,得自己 wrap 一层np.clip
目标函数里 print 会导致进化中断或卡死
多进程模式下(pool.map 或 multiprocessing.Pool),直接在目标函数里 print 可能引发输出缓冲冲突,表现是程序假死、CPU 占满但无进展,或报 OSError: [Errno 9] Bad file descriptor。
- 调试时改用
logging.info并配置logging.basicConfig(level=logging.INFO) - 或者加锁:
from multiprocessing import Lock; print_lock = Lock(),然后with print_lock: print(...) - 更稳妥的做法是把中间结果存到文件或共享内存,而不是实时打印
- 注意:Windows 下
spawn启动方式会让模块重载,print可能出现在错误进程中,现象更难排查
进化算法不保证找到全局最优,但能避开梯度陷阱
它对初始点不敏感,适合 scipy.optimize.minimize(method="BFGS") 容易陷在局部极小的函数,比如含多个尖峰、平台区或离散跳变的目标。
- 别指望它在 100 次迭代内搞定 100 维问题;典型实践是:先用
differential_evolution粗搜(maxiter=1000),再把结果当起点交给minimize(method="L-BFGS-B")精调 - 若目标函数本身有随机性(如蒙特卡洛模拟),进化算法会抖动,此时必须固定
random.seed或在目标函数里设np.random.seed(int(np.abs(x).sum()*1e6) % 2**32) - 收敛判断别只看
success字段——它只表示达到tol,而tol默认是1e-2,对工程精度常不够,得人工检查result.fun是否稳定
真正麻烦的是目标函数不可导又带硬约束,这时候进化策略的“试错”本质才体现价值,但你要自己把约束转成罚函数,而且罚权重得反复调——这步没标准答案,只能靠多次运行观察分布。
Python免费学习笔记(深入):立即使用
在学习笔记中,你将探索 Python 的核心概念和高级技巧!











