基于 PSO-master(通用变维粒子群优化库)。
编译执行环境:GCC 13.2.0(Wandbox 在线编译器,真实编译并执行) ;随机种子固定为
srand(12345)。下方"运行结果"为程序真实编译并执行后的标准输出,未做任何修饰。
1. 背景
Rosenbrock(香蕉函数)的全局极小位于一条狭长、弯曲的山谷底部,梯度信息指向山谷壁而非谷底,对几乎所有优化器都是经典难题。

2. 模型建立
Rosenbrock 函数:
f(x,y)=(1−x)2+100(y−x2)2f(x,y)=(1-x)^2+100(y-x^2)^2f(x,y)=(1−x)2+100(y−x2)2
定义域 x,y∈−2,2x,y\in-2,2x,y∈−2,2,全局极小在 (1,1) ,理论极小值 f=0。
| 参数 | 取值 |
|---|---|
| 维度 dim | 2 |
| 粒子数 | 60 |
| 迭代次数 | 700 |
| wstart → wend | 0.9 → 0.4(二次递减) |
| C1 / C2 | 1.49445 / 1.49445 |
| dt | 1.0 |
| 搜索下界 | -2.0, -2.0 |
| 搜索上界 | 2.0, 2.0 |
| 优化方向 | 最小化(fitness=-目标) |
3. 完整代码(PSO-master)
cpp
#include <iostream>
#include "PSO.h"
#include <math.h>
#define PI 3.141592653589793
// ===================== 案例7:二维 Rosenbrock 函数最小值(香蕉函数) =====================
// 狭长弯曲山谷,经典难例。
// 适应度:fitness = -( (1.0 - x) * (1.0 - x) + 100.0 * (y - x * x) * (y - x * x) ) - ( 0.0 )
double FitnessFunction(Particle& particle)
{
double x = particle.position_[0];
double y = particle.position_[1];
return -( (1.0 - x) * (1.0 - x) + 100.0 * (y - x * x) * (y - x * x) ) - ( 0.0 );
}
int main()
{
const int DIM = 2;
PSOPara psopara(DIM, true);
psopara.particle_num_ = 60;
psopara.max_iter_num_ = 700;
for (int k = 0; k < DIM; k++)
{
psopara.dt_[k] = 1.0;
psopara.wstart_[k] = 0.9;
psopara.wend_[k] = 0.4;
psopara.C1_[k] = 1.49445;
psopara.C2_[k] = 1.49445;
}
psopara.lower_bound_[0] = -2.0000;
psopara.upper_bound_[0] = 2.0000;
psopara.lower_bound_[1] = -2.0000;
psopara.upper_bound_[1] = 2.0000;
PSOOptimizer opt(&psopara, FitnessFunction);
std::srand(12345); // 固定随机种子,保证可复现
opt.InitialAllParticles();
for (int i = 0; i < opt.max_iter_num_; i++)
opt.UpdateAllParticles();
std::cout << "BEST_POS";
for (int k = 0; k < DIM; k++)
std::cout << " " << opt.all_best_position_[k];
std::cout << "\nBEST_FITNESS " << opt.all_best_fitness_ << std::endl;
return 0;
}
编译与运行(PSO.h、PSO.cpp 与案例源码同目录):
bash
g++ -O2 -std=c++11 case07.cpp PSO.cpp -o case07.exe
./case07.exe
4. 运行结果(真实执行输出)
text
BEST_POS 1 1
BEST_FITNESS -1.96996e-24
4.1 结果与理论解对比
| 项目 | 求得值(程序实际输出) | 理论解 | 误差 |
|---|---|---|---|
| 求得位置 | (1.000000, 1.000000) | (1.000000, 1.000000) | 欧氏距离 0.000000 |
| 目标函数值 | 0.000000 | 0.000000 | 绝对误差 0.000000 |
| 最优适应度 fitness | -0.000000 | --- | --- |
说明: Rosenbrock 狭长山谷难例,本配置下逼近 (1,1);更高维/更严格时可能只逼近谷底而非谷端点。
5. 小结与延伸
- Rosenbrock 山谷很窄,可尝试把
dt调到 0.5~0.8 以获得更细的步进;或改用自适应惯性权重。