
阅读科研论文时,我们经常会看到精巧的算法设计、复杂的数学公式,以及漂亮的实验收敛曲线。作者通过一系列 Benchmark、Baseline Comparison 和 Ablation Studies 展示方法的有效性,看起来整个研究过程严谨而完整。然而,当我们真正下载论文源码,尝试在自己的计算环境中复现这些结果时,才会发现,从"理解论文"到"验证论文",中间还有不少工作需要完成。
尤其是在进化计算(Evolutionary Computation)、机器学习和智能优化等领域,实验复现绝不仅仅是执行几条 Python 命令。它涉及源码版本管理、计算环境配置、依赖兼容性、算法参数、实验数据采集、统计分析以及科学可视化等多个环节。任何一个细节出现偏差,都可能导致实验无法运行,甚至得到与论文不同的结论。
最近,在阅读进化计算领域的研究论文时,我选择了 2026 年被 IEEE Transactions on Evolutionary Computation (IEEE TEVC)接收的论文 Evolutionary Generative Optimization: Towards Fully Data-Driven Evolutionary Optimization via Generative Learning (简称 EvoGO),开展了一次实验复现实践。
整个过程从阅读论文和获取官方源码开始,经历了 Mac M2 环境下的 JAX 兼容性问题、Python 模块导入问题、目标函数评价记录,以及使用 Matplotlib 绘制真实的 Convergence Curve。最终,在 Rosenbrock 5D 测试问题上完成了 600 次真实函数评价 ,获得了 Best Fitness = 5.3489 的实验结果,并生成了对应的收敛曲线。
这次实践让我进一步认识到,论文复现不仅是验证算法能否运行,更重要的是建立一套规范、可追溯、可重复使用的科研实验流程。本文将以 EvoGO 为例,介绍其研究背景与方法亮点,梳理实际复现过程中遇到的问题,并总结一套适用于后续进化计算、智能优化及机器学习研究的实验复现 SOP(Standard Operating Procedure)。
01. 研究背景:从传统进化计算走向生成式优化
1.1 传统进化算法面临什么问题?
进化计算(Evolutionary Computation,EC)是一类受生物进化机制启发的智能优化方法,其典型代表包括 Genetic Algorithm(GA)、Differential Evolution(DE)、Evolution Strategies(ES)和 Genetic Programming(GP)等。这类算法通常采用 Population-based Search,通过不断生成、评价和选择候选解,在复杂搜索空间中寻找较优方案。
与传统梯度优化方法相比,进化计算具有较强的适用性。对于不可微、非凸、带有复杂约束,或者只能通过仿真进行评价的 Black-box Optimization 问题,进化算法提供了一种不依赖显式梯度信息的搜索机制。因此,在工程设计、机器人控制、资源优化和复杂调度等领域,进化计算具有广泛的应用价值。
不过,传统进化算法也存在一个值得思考的问题:搜索方向、搜索步长以及新候选解的生成机制,为什么需要主要依赖人工设计的算子?
以经典 Differential Evolution 为例,其变异操作通常采用:
\\mathbf{v}*i = \\mathbf{x}* + F\\left(\\mathbf{x}*{r_2} - \\mathbf{x}* \\right)
其中,\\mathbf{x}*{r_1}、\\mathbf{x}* 和 \\mathbf{x}_{r_3} 表示种群中的不同候选解,F 是控制差分向量幅度的缩放因子。该机制利用种群个体之间的差异产生搜索方向,在很多优化问题中具有较好的表现。
但从算法设计角度来看,其基本搜索形式仍然是研究者预先指定的。当目标函数的结构、变量关系或优化景观发生变化时,这些操作未必始终适合当前问题。
近年来,研究人员开始将机器学习引入进化计算,希望利用优化过程中积累的数据改善搜索效率。例如,Surrogate-Assisted Evolutionary Algorithms 利用代理模型近似昂贵的目标函数,Estimation of Distribution Algorithms 通过建模优良解的分布指导采样,而 Generative Modeling-based Evolutionary Algorithms 则进一步尝试通过生成式学习产生新的候选解。
这一研究趋势背后的核心思想是:能否让优化算法从历史搜索经验中学习更加有效的搜索机制,而不是完全依赖人工预设的操作规则?
1.2 EvoGO 的基本信息
EvoGO 正是在这样的研究背景下提出的。
| 项目 | 内容 |
|---|---|
| Title | Evolutionary Generative Optimization: Towards Fully Data-Driven Evolutionary Optimization via Generative Learning |
| Authors | Tao Jiang, Kebin Sun, Zhenyu Liang, Ran Cheng, Yaochu Jin, Kay Chen Tan |
| Year | 2026 |
| Journal | IEEE Transactions on Evolutionary Computation |
| DOI | 10.1109/TEVC.2026.3664432 |
| Research Area | Evolutionary Computation、Generative Learning、Black-box Optimization |
| Open-source Code | EMI-Group/evogo |
这篇论文关注的核心问题是:如何通过数据驱动的生成式学习机制,替代进化算法中传统的人工设计搜索算子,使算法能够从历史优化结果中学习产生更优候选解的方法。
论文提出的 EvoGO 框架,将优化过程组织为三个阶段:
- Data Preparation:利用历史评价数据进行精英筛选、可选的数据增强,以及较优解和较差解之间的配对。
- Model Training:结合代理模型与双向生成模型,通过专门设计的损失函数训练搜索映射。
- Population Generation:使用训练后的生成模型产生下一代候选解,并通过真实目标函数进行评价。
其核心搜索机制可以表示为:
\\mathbf{x}*{t+1} = \\gamma* \\left(\\mathbf{x}_t\\right)
其中,\\mathbf{x}*t 表示当前候选解,\\gamma* 表示经过历史数据训练的生成模型,\\mathbf{x}_{t+1} 则是新生成的候选解。
与传统 GA、DE 等方法显式执行交叉或变异不同,EvoGO 希望通过神经网络学习一个从当前解到新解的映射。搜索方向和变化幅度不再完全由固定算子定义,而是隐含在模型学习到的变换关系中。
1.3 值得关注的三个亮点
亮点一:从学习 Fitness Function 转向学习 Search Operator。 传统 Surrogate-Assisted Evolutionary Algorithms 通常使用代理模型估计候选解的目标函数值,从而减少昂贵的真实函数评价。EvoGO 则进一步将 Candidate Generation Process 作为学习对象,希望模型直接学习如何从现有解生成更好的解。这意味着机器学习不只是辅助评价,还开始参与优化器本身的搜索机制构建。从方法论角度看,这种思路与 Learning-based Optimization、Learned Optimizers 等研究方向存在重要联系。
亮点二:将生成模型训练目标与优化目标结合。 普通生成模型往往关注生成样本与目标数据之间的相似程度,但在优化问题中,生成结果与历史较优解相似,并不代表它一定能够取得更好的目标函数值。EvoGO 通过组合 Similarity Loss、Reconstruction Loss 和 Optimization Loss,将生成式学习与代理模型提供的优化信息结合,使模型不仅学习较优解的特征,还尝试学习有效的搜索方向。
亮点三:在高维优化与并行计算中展示了潜力。 论文覆盖数值优化、经典控制和机器人控制等不同任务,测试维度最高达到 1000D。作者报告,EvoGO 在多个高维 Benchmark 上取得了有竞争力的结果,并在特定 GPU 并行控制实验中表现出明显的时间效率优势。
这些结果值得关注,但也需要谨慎理解。例如,论文中的"10 Generations"不能直接等同于只需要 10 次真实函数评价,而静态 Benchmark 上的性能表现,也不能直接证明模型具有动态环境下的鲁棒性或跨任务泛化能力。正因为论文包含了生成模型、代理模型和多阶段优化流程,它非常适合作为研究算法机制与实验复现方法的案例。

02. 论文复现不仅是把代码运行起来
在软件工程中,我们通常需要保证系统能够正确执行、满足功能要求,并达到预期性能。而在科学研究中,实验还承担着验证假设、支持研究结论和排除替代解释的任务。因此,对于一篇算法论文,仅仅能够运行作者的代码,并不能认定已经完成了论文复现。
科研论文实验复现可以划分为三个实践层次:
| 层次 | 英文 | 主要目标 |
|---|---|---|
| Level 1 | Functional Reproduction | 验证算法可以完整运行 |
| Level 2 | Experimental Reproduction | 在可比条件下重新验证论文的实验结果 |
| Level 3 | Mechanism Investigation | 研究算法为何有效,以及在什么条件下失效 |
Functional Reproduction 主要解决工程层面的问题,包括依赖安装、源码兼容、模型初始化、数据处理、算法执行和结果输出。其成功标准是能够完成一个端到端的实验,而不是仅仅成功导入某个 Python 模块。
Experimental Reproduction 则进一步要求实验条件具有可比性,包括相同或明确记录差异的 Benchmark、问题维度、随机种子协议、Evaluation Budget、算法超参数、Baseline 和统计方法。
Mechanism Investigation 更接近研究工作本身。完成基本复现后,研究者可以通过消融实验、参数敏感性分析、搜索方向可视化和动态环境测试,检验论文提出的机制究竟发挥了什么作用。
对于 EvoGO,本次首先选择最简单、最可控的 Rosenbrock 5D 测试问题,希望在不引入过多实验复杂性的情况下,验证其完整优化流程,并获得可以用于绘制收敛曲线的真实数据。
03. 实验准备:获取源码与构建独立环境
3.1 获取官方源码并记录版本
本次使用 EvoGO 官方公开的 GitHub 仓库:
bash
git clone https://github.com/EMI-Group/evogo.git
cd evogo
下载源码之后,建议第一时间执行:
bash
git rev-parse HEAD
这条命令用于获取当前 Git Commit Hash。为什么要记录 Commit?因为论文公开之后,作者可能继续维护代码,包括修复 Bug、升级依赖、修改默认参数或增加新的功能。如果没有记录源码版本,未来即使使用相同的实验命令,也未必能够得到可比的结果。对于科研复现来说,代码版本与实验参数一样,都是实验条件的重要组成部分。
3.2 创建独立的 Python 虚拟环境
本次实验使用的硬件与软件环境为:
| 组件 | 实验环境 |
|---|---|
| Computer | Apple Mac M2 |
| Architecture | ARM64 |
| Operating System | macOS |
| Python | 3.11 |
| Framework | JAX |
| Computing Device | CPU |
| Visualization | Matplotlib |
| Environment Management | virtualenvwrapper |
采用 virtualenvwrapper 创建独立的 Python 环境:
bash
mkvirtualenv --python="$(which python3.11)" paper_evogo
后续使用:
bash
workon paper_evogo
检查环境:
bash
python --version
python -c "import platform; print(platform.machine())"
创建独立虚拟环境是一个非常值得长期坚持的习惯。不同科研项目对 Python、JAX、PyTorch、NumPy 等依赖库的版本要求可能不同,如果所有项目共享同一个环境,很容易因为升级一个包而影响其他实验。
另外,复现旧代码时并不一定要使用最新版本的 Python。本次最初使用较新的 Python 版本,后来调整到 Python 3.11,主要是为了减少与作者源码及依赖配置之间的兼容性问题。
3.3 Apple M2 与 NVIDIA CUDA 的兼容性问题
EvoGO 官方仓库提供 JAX 与 PyTorch 两套实现,但部分依赖配置包含 NVIDIA CUDA 相关组件。由于 Apple M2 并不支持 NVIDIA CUDA,不能直接照搬作者面向 NVIDIA GPU 的安装配置。本次选择 JAX CPU 作为初始复现环境,以便先验证算法逻辑和小规模 Benchmark。
基础依赖包括:
bash
python -m pip install \
jax flax optax chex \
numpy scipy pandas matplotlib
需要注意的是,这只是安装基础依赖的一种方式,并不代表任何版本组合都能够直接兼容作者代码。对于正式复现,仍需要在成功运行后保存完整的依赖版本,并检查是否存在 API 变化或数值计算行为差异。
检查依赖:
bash
python -m pip check
检查 JAX:
python
import jax
print(jax.__version__)
print(jax.devices())
本次使用的是 Mac M2 CPU,而不是论文部分实验所采用的 GPU 并行环境。因此,后续的运行时间结果不适合直接与作者报告的 GPU 效率进行比较。
04. 实验中遇到的问题:从报错到定位与修复
实际复现过程中,先后遇到了 JAX API 不兼容、依赖缺失、Python 模块路径错误等问题。虽然这些问题并不涉及 EvoGO 的核心数学模型,但它们直接决定了实验能否顺利进行。
4.1 JAX API:enable_x64 导入失败
第一次导入 EvoGO 时,程序报错:
text
ImportError: cannot import name 'enable_x64'
from 'jax.experimental'
检查源码后发现,evogo_jax/models.py 使用了旧版 JAX 的导入方式:
python
from jax.experimental import enable_x64
而当前 JAX 版本需要调整为:
python
from jax import enable_x64
修改后,程序继续执行。这类问题的处理原则是:优先修复 API 兼容性,而不是随意改变算法本身的计算逻辑。 例如本次只修改导入路径,保留作者原来使用局部 64 位精度计算的设计。
4.2 缺失依赖:chex
随后出现:
text
ModuleNotFoundError: No module named 'chex'
这是一个典型的依赖缺失问题。Chex 是 JAX 生态中的辅助工具库,安装后即可继续进行模块导入测试:
bash
python -m pip install chex
这一步也说明,源码公开并不意味着项目的依赖环境一定能在不同操作系统和硬件上直接复现。依赖的完整性、版本约束和可安装性,本身就是科研软件可复现性的一部分。
4.3 Python 模块搜索路径问题
在项目根目录运行测试脚本时,EvoGO 可以正常导入。但将独立实验脚本放入 repro/ 子目录后,出现:
text
ModuleNotFoundError: No module named 'evogo_jax'
原因不是缺少源码,而是 Python 执行脚本时的模块搜索路径发生了变化。最终采用模块方式运行:
bash
python -m repro.run_logged
解决了本次问题。从工程实践角度看,科研项目也需要良好的代码组织方式。将作者源码、实验运行逻辑、数据处理和绘图脚本分离,有利于后续复现、维护和扩展。
4.4 JAX 的 clip() 参数不兼容
算法运行到 Population Generation 阶段后,出现:
text
TypeError: clip() got an unexpected keyword argument 'a_max'
原始代码为:
python
jnp.clip(
new_datasets_x,
a_min=-0.25,
a_max=1.25
)
修改为:
python
jnp.clip(new_datasets_x, -0.25, 1.25)
保留了原有的裁剪范围,只改变了调用参数的写法。这个错误发生在新候选解处理阶段,也说明程序在此之前已经进入了 EvoGO 的核心优化流程。
4.5 从这些报错中得到的经验
回顾上述问题,可以将常见科研代码错误归纳为四类:
| 问题类型 | 典型表现 | 优先检查 |
|---|---|---|
| Dependency Issue | 找不到 Python 包 | Requirements、Virtual Environment |
| API Compatibility | 函数或参数不存在 | Library Version、API Documentation |
| Import Path Issue | 找不到项目模块 | Working Directory、Python Path |
| Runtime / Numerical Issue | NaN、异常退出、训练不收敛 | 数据、数值精度、算法参数 |
对于科研论文复现,最重要的原则是:采用最小修改策略,并完整记录对原始代码的改动。 本次使用 Git 检查源码变化:
bash
git diff
并保存修改补丁:
bash
git diff > source_changes.patch
如果后续实验结果与论文不同,这些修改记录将帮助判断差异来自算法、依赖、计算环境还是代码实现。
05. 最小可运行实验:Rosenbrock 5D
5.1 为什么从简单 Benchmark 开始?
完成环境配置后,没有直接尝试论文中的 200D、404D 或 1000D 优化问题,而是选择作者示例中提供的 Rosenbrock 5D。
Rosenbrock 是连续优化领域经典的测试函数,常用于评价算法在具有狭窄、弯曲低目标值区域的搜索景观中的表现。其标准形式为:
f(\\mathbf{x}) = \\sum_{i=1}^{d-1}\\left\[100\\left(x_{i+1}-x_i^2\\right)\^2 + \\left(1-x_i\\right)\^2\\right\]
其中,d 表示决策空间维度,标准函数的全局最优目标值为 0。需要注意的是,EvoGO 官方实现采用归一化决策空间及相应的变量转换,因此程序返回的解向量不应直接理解为标准 Rosenbrock 函数的原始坐标。
对于初步复现,选择低维 Benchmark 有两个好处。首先,它能够降低实验计算成本,快速验证算法是否完整运行;其次,较低维度更方便检查 Fitness Evaluation、候选解生成与结果记录是否符合预期。
5.2 实验配置与运行代码
本次采用以下配置:
| 参数 | 数值 |
|---|---|
| Benchmark | Rosenbrock |
| Dimension | 5 |
| Random Seed | 42 |
| Population Size | 100 |
| Maximum Generations | 5 |
| Generative Model Batch Size | 100 |
| Computing Device | Mac M2 CPU |
核心代码如下:
python
import jax
from evogo_jax.evogo import EvoGO
from test_functions.simple_functions_jax import Rosenbrock
dim = 5
seed = 42
problem = Rosenbrock(
dim=dim,
key=jax.random.PRNGKey(seed),
parallels=1
)
solver = EvoGO(
max_iter=5,
batch_size=100,
gm_batch_size=100,
num_parallel=1,
debug=True
)
best_x, best_y = solver.solve(
problem,
dim=dim,
seed=seed
)
print("Best solution:", best_x)
print("Best fitness:", best_y)
程序执行时,会先建立初始种群和历史评价数据,再训练 Gaussian Process 代理模型以及生成模型,随后通过 Population Generation 产生新的候选解,并调用真实 Rosenbrock 函数进行评价。这一过程对应 EvoGO 论文中描述的主要方法流程,也验证了从数据准备到真实优化评价的基本执行链路。
5.3 本次实验结果
经过兼容性修复后,实验最终成功完成,并得到:
text
Best solution:
[0.4764284 0.45906833 0.45622092
0.4531083 0.45464852]
Returned best fitness:
5.348946571350098
Objective evaluations:
600
其中,最终 Best Fitness 约为 5.3489 ,累计真实函数评价次数为 600 FEs。
本次实验初始种群包含 100 个候选解,之后执行 5 次种群更新,每次评价 100 个解,因此:
\\mathrm{FEs} = 100 + 5\\times100 = 600
这一计算结果与实验日志一致。但需要强调,EvoGO 实验中的 Training Loss 与目标函数 Fitness 并不是同一个概念。前者主要反映代理模型或生成模型训练目标的变化,后者才是原始 Rosenbrock 优化问题的结果。
本次实验最重要的成果,不是得到一个具体的 Fitness 数值,而是确认了:EvoGO 可以在当前 Mac M2 环境中完整执行优化流程,并且能够通过真实目标函数评价验证生成模型产生的新候选解。
06. 科研实验为什么必须记录完整的中间数据?
运行作者示例时,程序通常会输出最终 Best Solution 和 Best Fitness。对于功能测试而言,这已经能够验证算法是否正常结束;但对于论文复现和实验分析来说,单个最终数值显然不够。
例如,已知最终 Fitness 为 5.3489,我们仍然无法回答:算法是在前两代就取得了主要进展,还是每代都持续改善?搜索过程中是否出现停滞?如果改变随机种子,结果是否稳定?如果加入 CMA-ES 或 DE,谁能够在相同评价预算下取得更好的性能?要回答这些问题,就需要在实验执行过程中记录中间数据。
本次在项目中增加了独立的 repro/ 目录,将实验运行、原始数据和绘图过程分开管理:
text
evogo/
├── evogo_jax/
├── evogo_torch/
├── test_functions/
├── repro/
│ ├── run_logged.py
│ ├── plot_fig3.py
│ ├── plot_fig7.py
│ ├── results/
│ ├── figures/
│ └── vectors/
└── README.md
其中,run_logged.py 负责运行优化实验并记录评价数据,results/ 保存 CSV,figures/ 保存科研图表,vectors/ 则计划用于后续搜索方向可视化的数据采集。
对于进化计算论文,建议至少记录以下字段:
| Field | Description |
|---|---|
| Algorithm | 算法名称 |
| Benchmark | 测试问题 |
| Dimension | 问题维度 |
| Seed | 随机种子 |
| Generation | 当前种群代数 |
| FE | 累计真实函数评价次数 |
| Best Fitness | 历史最优目标函数值 |
| Runtime | 计算耗时 |
此外,正式实验最好保存完整的配置文件、依赖版本、硬件信息和源码 Commit,而不是只依赖 CSV 文件名记录实验条件。
这里尤其需要区分 Generation、Fitness Evaluation 和 Wall-clock Time。前者描述算法更新种群的次数,第二个指标描述真实目标函数被调用的次数,第三个指标则衡量实际时间成本。对于 EvoGO 这类包含生成模型训练和代理模型优化的方法,即使两种算法使用相同的 FEs,额外模型训练成本也可能存在明显差异。因此,严格的性能比较应同时关注解质量、评价预算和总计算成本。
07. Matplotlib 实战:复现 Convergence Curve
7.1 Figure 3 表达的是什么?
EvoGO 论文的 Figure 3 对比了多个优化算法在不同 Benchmark 上的收敛表现。这类图通常以 Function Evaluations 为横轴,以目标函数值为纵轴,展示算法在给定评价预算下的优化过程。
为了理解论文中的绘图逻辑,本次首先使用 Rosenbrock 5D 的真实实验数据,绘制 EvoGO 单次运行的收敛曲线。
对于最小化问题,常用的 Best-so-far Fitness 定义为:
f_{\\mathrm{best}}(t) = \\min_{1\\le i\\le t} f\\left(\\mathbf{x}_i\\right)
也就是说,在每一个评价时刻,记录迄今为止找到的最优目标函数值。由于始终保留历史最优解,因此在最小化问题中,Best-so-far Fitness 应当单调不增。
7.2 绘图命令与输出
本次将真实评价结果保存为:
text
repro/results/rosenbrock_5d_seed42_curve.csv
然后使用 Matplotlib 绘图脚本:
bash
python -m repro.plot_fig3 \
--files \
repro/results/rosenbrock_5d_seed42_curve.csv \
--out \
repro/figures/figure3_single.pdf \
--logy
其中,--logy 表示采用对数纵轴。由于本次 Fitness 从上万下降到个位数,使用 Log Scale 可以更清晰地展示不同优化阶段的变化。图表输出为 PDF 矢量文件,能够用于后续论文排版,并且可以直接通过原始 CSV 重新生成。
配图位置: 此处插入本次实验实际生成的
figure3_single.pdf(发布前可导出为高清 PNG)。建议图注: EvoGO 在 Rosenbrock 5D 上的单次运行收敛曲线。横轴为累计真实 Function Evaluations,纵轴为 Best-so-far Fitness,采用对数刻度。Seed = 42,Population Size = 100。
7.3 如何科学地分析这张图?
从实验曲线可以观察到,初始 Best Fitness 约为 19,426,经过 600 次真实函数评价后下降至约 5.3489。整个过程中,Best-so-far Fitness 持续下降,说明算法在本次运行中不断发现更好的候选解。
按照图中的评价点观察,在 100--200 FEs 之间,算法实现了明显的目标值下降;在 200--400 FEs 阶段,优化过程继续改善;到 600 FEs 时,算法仍然能够取得更低的 Fitness,没有观察到明显的长时间停滞。
相对于初始值,最终目标函数值下降约 99.97%。不过,这并不意味着算法已经收敛到全局最优,因为 Rosenbrock 标准函数的理论最优目标值为 0,而当前结果仍然存在一定距离。
此外,这张图仅包含 一次独立运行(n=1)。因此,它能够说明本次运行的优化行为,却不能提供有意义的运行间标准差,也不能据此判断算法的统计稳定性。
这也是实验分析中值得反复提醒自己的一点:一条漂亮的收敛曲线,可以展示一次实验的过程,却不能单独证明一种算法具有普遍的性能优势。
08. 从单次结果走向统计可信的实验结论
进化算法通常具有随机性,包括初始种群生成、采样和训练过程中的随机因素。不同随机种子可能导致不同的搜索轨迹,进而产生不同的最终结果。因此,正式的算法论文通常需要开展多次独立运行,而不是仅报告表现最好的实验。
对于 R 次独立运行,如果每次都在相同的 Function Evaluation Budget 下记录历史最优 Fitness,可以计算:
\\bar f_t = \\frac{1}{R}\\sum_{r=1}\^{R} f_t\^{(r)}
其中,\\bar f_t 表示第 t 个评价预算位置的平均 Fitness。相应的样本标准差为:
s_t = \\sqrt{\\frac{1}{R-1}\\sum_{r=1}^{R}\\left(f_t^-\\bar f_t\\right)\^2}
最终绘制 Mean ± Standard Deviation,可以观察算法的平均优化趋势及运行结果波动。在实际实验中,还应注意不同算法可能在不同 FE 位置记录结果。因此,进行统计计算之前,需要先采用合理的评价预算对齐方法,不能简单地按 CSV 行号计算平均值。
本次已经完成单个 Seed 的实验,下一步计划扩展到多个随机种子,并逐步加入 CMA-ES 等 Baseline,对不同方法进行公平比较。
除了 Mean 和 Standard Deviation,后续还可以进一步考虑 Median、Interquartile Range、Confidence Interval、Effect Size 和适当的统计显著性检验。对于多算法、多 Benchmark 的比较,实验结论应建立在相同预算、明确参数设置和可靠统计分析的基础上,而不只是比较一张图中哪条曲线下降得更快。
09. 从性能曲线走向算法机制:Figure 7 的下一步计划
收敛曲线主要回答算法取得了什么结果,而研究算法机制还需要回答另一个问题:为什么它能够产生更好的候选解?
EvoGO 论文中的 Figure 7 展示了生成模型在二维 Ackley 优化景观中的搜索方向变化,这为理解 Learned Search Operator 提供了一个比较直观的方式。
对于当前候选解:
\\mathbf{x}_{\\mathrm{in}}
生成模型产生:
\\mathbf{x}*{\\mathrm{out}} = \\gamma\\left(\\mathbf{x}* {\\mathrm{in}}\\right)
由此得到搜索位移:
\\Delta\\mathbf{x} = \\mathbf{x}*{\\mathrm{out}} - \\mathbf{x}* {\\mathrm{in}}
其步长为:
s = \\left\|\\Delta\\mathbf{x}\\right\|_2
通过使用 Matplotlib 的 contourf() 绘制 Ackley Fitness Landscape,再通过 quiver() 绘制搜索向量,就能够观察生成模型是否将候选解引导到更加有利的区域。
与 Figure 3 相比,Figure 7 更接近算法行为分析。除了观察箭头方向,还可以计算生成前后的真实 Fitness 差异,进一步衡量搜索方向的有效性。
例如,定义:
\\Delta f_i = f\\left(\\mathbf{x}*{\\mathrm{out},i}\\right) - f\\left(\\mathbf{x}* ,i}\\right)
对于最小化问题,当 \\Delta f_i\<0,表示这次生成式变换改善了目标函数值。进一步可以统计 Improvement Rate、Average Step Size 和 Population Diversity 等指标,观察模型在不同 Generation 中如何调整搜索行为。
这部分实验目前尚未完成。后续计划在 Ackley 2D 上记录生成模型的输入和输出,并比较不同 Generation 的搜索方向与步长。相比单纯绘制一张与论文相似的图,更希望通过这项实验理解:生成模型到底学习到了什么搜索规律?它在哪些区域能够产生有效改进?当目标景观变复杂时,这些规律是否仍然成立?
10. 建立一套可复用的科研论文实验复现 SOP

经过本次实践,以后复现进化计算或机器学习论文时,可以采用相对固定的标准流程,将论文分析、工程运行、实验验证和科研探索连接起来。
| Stage | 核心工作 | 交付成果 |
|---|---|---|
| 01. Paper Analysis | 研究算法、数学模型、Benchmark 和实验设计 | Paper Notes |
| 02. Source Code Management | 获取源码、记录 Commit 和变更 | Source Record |
| 03. Environment Setup | 建立独立虚拟环境并安装依赖 | Environment Specification |
| 04. Compatibility Testing | 处理依赖、API 和运行问题 | Compatibility Patch |
| 05. Minimal Reproduction | 运行最小 Benchmark | Valid Experimental Run |
| 06. Experiment Logging | 记录 Seeds、FEs、Fitness 和 Runtime | Raw Experimental Data |
| 07. Visualization | 绘制收敛曲线与机制图 | Reproducible Figures |
| 08. Statistical Evaluation | 重复运行、比较 Baselines、统计检验 | Statistical Results |
| 09. Critical Evaluation | 分析结果差异、机制与局限 | Reproduction Report |
| 10. Research Exploration | 提出可检验的新研究问题 | Research Hypotheses |
在执行这套 SOP 时,有三个原则需要特别坚持。
10.1 原则一:尽可能保留原始算法实现
对于科研复现,不能为了让程序成功运行,就随意修改算法参数、目标函数定义或损失函数逻辑。否则,最后验证的可能已经不再是论文原始方法。
对于必须处理的兼容性问题,应坚持 Minimal Modification,并保存 Git Diff。更规范的做法是为实验固定源码 Commit、依赖版本和运行环境,确保未来能够追溯。
10.2 原则二:实验执行与结果可视化分离
算法运行负责生成真实数据,Matplotlib 负责读取数据并绘制图表。两者不应紧密耦合。
这样的设计具有很高的实践价值。例如,当需要修改图表字体、坐标轴、误差范围或者增加新的 Baseline 时,只需要重新运行绘图脚本,而不必重新执行昂贵的优化实验。对于涉及大量 Function Evaluations 或真实系统仿真的研究,这种分离可以节省大量时间,也更容易保证图表的可复现性。
10.3 原则三:保留原始数据,而不是只保留最终结果
科研实验应尽可能保存完整的 Raw Data,包括不同 Seeds、每代 Fitness、评价次数、运行时间以及对应的实验配置。最终的图表、统计结果和论文表格,最好都能够通过原始数据重新计算生成。
这样,当未来发现某个结果存在异常,或者需要采用新的统计方法重新评价算法时,就不必重新开始整个实验。从长期研究积累的角度看,源码、实验配置、原始数据、可视化脚本和研究笔记,应当构成一个完整的科研实验资产。
11. 从实验复现进一步走向独立科研问题
科研论文复现并不是研究工作的终点。恰恰相反,在能够独立运行和评价算法之后,才有条件进一步分析方法的适用边界,并提出新的科学问题。
以 EvoGO 为例,论文在多个静态优化任务中验证了生成式搜索的效果,但这并不意味着学习到的搜索映射一定能够适应动态变化的环境。
假设优化目标随时间变化:
f_t\\left(\\mathbf{x}\\right) \\neq f_{t+1}\\left(\\mathbf{x}\\right)
那么当前生成模型所学习的搜索方向,可能不再适合变化后的优化景观。
对于云资源分配(Cloud Resource Allocation)问题,这种情况尤为常见。实际系统中的 Workload、Service Topology、Resource Capacity 和 SLO Requirements 可能持续变化,优化算法不仅需要在当前环境中找到较优配置,还需要在环境改变之后维持可靠的优化能力。
这自然引出了几个值得进一步研究的问题:生成式搜索算子对目标景观变化是否敏感?当 Surrogate Model 出现预测偏差时,生成模型是否会放大这种偏差?能否通过环境状态建模、变化检测或自适应训练,提高优化算法的 Robustness 和 Generalization?
这些问题并不能仅凭 EvoGO 一篇论文就被认定为整个研究领域尚未解决的空白,但它们可以成为后续 Literature Review、机制分析和独立实验的切入点。
从这一角度来看,论文复现不仅是验证已有研究,更是在建立一条从理论理解到原创性研究的路径:
Paper Understanding → Reproduction → Mechanism Analysis → Research Gap Investigation → Hypothesis Testing
当这一过程能够持续、规范地执行时,论文阅读与实验实践就不再是两项独立工作,而会逐渐形成相互促进的研究循环。
12. 总结与思考
回顾本次 EvoGO 复现实践,从阅读论文、下载源码,到搭建 Apple M2 的 JAX 环境,再到解决 API 兼容性问题、运行 Rosenbrock 5D Benchmark、记录 600 次真实函数评价并绘制收敛曲线,整个过程涉及的内容远不止算法本身。
当前已完成的是 EvoGO 的小规模端到端运行,以及基于真实实验数据的单次 Convergence Curve 可视化。这验证了算法能够在当前环境中执行,也为后续实验建立了数据记录与绘图流程。但多随机种子统计、严格 Baseline Comparison 和 Figure 7 的 Search Direction Visualization 等工作仍需要继续完成。
这次实践也让我更加明确,科研复现的价值不仅在于得到一个与论文接近的结果,更在于理解结果是如何产生的,以及研究结论建立在什么实验条件和证据基础之上。
对于后续进化计算、动态优化、鲁棒优化和云资源调度等方向的研究,可以逐步将这套 SOP 固定下来:每阅读一篇值得深入研究的论文,尽可能将文献分析、源码验证、实验数据、统计结果和 Critical Observations 形成完整记录。
长期积累下来,这些材料不仅可以帮助研究者快速回顾某篇论文,更能够形成可追溯、可比较、可扩展的个人科研知识库。
从读懂一篇论文,到能够独立验证其实验;从复现已有结果,到理解算法的有效机制与适用边界------这正是科研实验复现真正值得长期坚持的价值。
参考资料(References)
1 Jiang, T., Sun, K., Liang, Z., Cheng, R., Jin, Y., & Tan, K. C. (2026). Evolutionary generative optimization: Towards fully data-driven evolutionary optimization via generative learning . IEEE Transactions on Evolutionary Computation . Accepted manuscript. https://doi.org/10.1109/TEVC.2026.3664432
2 EMI-Group. EvoGO: Evolutionary Generative Optimization Source code. GitHub. https://github.com/EMI-Group/evogo
3 JAX Developers. JAX Documentation . https://docs.jax.dev/
4 Matplotlib Development Team. Matplotlib Documentation . https://matplotlib.org/stable/
5 Python Software Foundation. Python Documentation . https://docs.python.org/3/
6 Git Project. Git Reference . https://git-scm.com/docs