aider 如何评测 GPT-4 Turbo with Vision:代码编辑基准测试与“懒惰编码”现象解析
OpenAI 于 2024 年 4 月发布的 GPT-4 Turbo with Vision(gpt-4-turbo-2024-04-09)在 aider 的两套代码基准测试中均落后于此前所有 GPT-4 模型:代码编辑基准得分 62%,重构基准(专门测量“懒惰编码”)仅得 34%。本文基于 aider 仓库中的评测文章 GPT-4 Turbo with Vision is a step backwards for coding 展开,完整继承原文的评测结论与数据,并结合 aider/models.py、aider/resources/model-settings.yml、aider/coders/base_coder.py 等源码,讲清这个模型在 aider 中是如何被支持、被调优(“anti-lazy”提示词机制)以及默认模型选择策略的演进。
评测背景:aider 的两套代码基准测试
要理解评测结论,先要看清 aider 用来量化 LLM 编码能力的两套测试集。
代码编辑基准:133 道 Exercism Python 练习
aider 依赖一套代码编辑基准测试来定量评估 LLM 修改既有代码的能力。该基准使用 aider 尝试完成 133 道来自 Exercism Python 的编程练习,每道题的素材包括:markdown 格式的任务说明、一份只含函数/类骨架的 stub 实现文件,以及单独的单元测试文件。
每个练习 LLM 有两次机会:
- 第一次尝试:LLM 拿到初始 stub 代码和任务的英文描述。如果全部测试通过,该题完成;
- 若有任何测试失败,aider 把失败的测试输出回传给 LLM,让它带着错误信息再试一次。
这个流程在基准实现文档中有明确描述:第一次尝试时 aider 发送实现文件内容、任务说明和一条固定指令(要求保留 stub、只使用标准库);测试失败后第二次尝试只附带前 50 行测试错误输出,以避免超出小模型的上下文窗口,并附一条“测试是正确的,请修改代码解决错误”的收尾指令(见 benchmarks.md 中对两次尝试流程的完整描述)。
“懒惰”重构基准:89 个 Python 重构任务
GPT-4 Turbo 的 “preview” 系列模型长期因“懒惰编码”被诟病:它们在写代码时经常省略需要的实现,转而留下一条“homework”式注释,例如:
def some_complex_method(foo, bar):
# ... implement method here ...
为诱发并量化这种偷懒行为,aider 维护了一个专门的“laziness”基准测试套件,由 89 个 Python 重构任务组成——这些任务的特点正是容易诱发 GPT-4 Turbo 写出上述那种省略实现的代码。它要求 LLM 重构大 Python 类中的大方法,检验模型能否输出长段完整代码而不跳过任何部分。
结论一:代码编辑能力,GPT-4 Turbo with Vision 是 GPT-4 家族最低分
在 133 道 Exercism 练习的代码编辑基准上:
- GPT-4 Turbo with Vision 仅得 62%,是现有 GPT-4 模型中的最低分;
- 其他 GPT-4 模型的得分区间为 63%–66%。
原文指出,这一差距属于小幅回退(small regression),与 gpt-4-0613 相比可能不具统计显著性——也就是说,新模型并没有“断崖式”变差,但方向上是负面的。
值得补充的是,在 aider 的编辑格式排行榜数据中,gpt-4-turbo-2024-04-09 分别以 udiff(unified diff)和 diff 两种编辑格式跑过完整基准(对应的复现命令记录为 aider --model gpt-4-turbo-2024-04-09),说明评测覆盖了多种编辑格式而非单一配置。
结论二:“懒惰编码”显著加剧,34% 分是 GPT-4 Turbo 系列最懒
在 89 个重构任务的 laziness 基准上:
GPT-4 Turbo with Vision 仅得 34%,以显著差距成为所有 GPT-4 Turbo 模型中“最懒”的 coder。
这个 34% 与前文“仅小幅回退”的 62% 形成鲜明对比:新模型在简单代码编写任务上只是略逊,但在需要输出长段完整代码、不允许跳水的重构任务上明显退步——这正是“懒惰编码”(用 # implement method here 注释代替真实实现)最容易被放大的场景。
源码印证:aider 如何支持并“对抗”这个模型
原文结论部分提到,aider 完整支持新模型,可用 --model gpt-4-turbo-2024-04-09 访问。下面从仓库源码逐层印证这条链路,并说明“anti-lazy”机制的具体实现。
1. 模型注册:OPENAI_MODELS 列表与模型别名
aider/models.py 中的 OPENAI_MODELS 常量列出了所有被 aider 认可的 OpenAI 模型名,其中包含 gpt-4-turbo 与带日期的快照版本 gpt-4-turbo-2024-04-09(第 47–48 行)。同时,同文件的 MODEL_ALIASES(第 99–123 行)定义了别名映射:
"4-turbo": "gpt-4-1106-preview",
也就是说,在 aider 的别名体系里,4-turbo 这个简称并不指向带 Vision 的新模型,而是固定解析到 gpt-4-1106-preview——这与原文“继续把 gpt-4-1106-preview 作为 GPT-4 家族默认/首选”的结论一致。旧式别名(如 4_turbo)在 aider/deprecated.py 中同样映射到 gpt-4-1106-preview,并有对应测试 tests/basic/test_deprecated.py 固化这一行为。
2. 每模型参数:model-settings.yml 中的配置块
每个模型在 aider 中不只是名字,还携带一组“调优参数”。aider/resources/model-settings.yml 中该模型的配置为:
- name: gpt-4-turbo-2024-04-09
edit_format: udiff
weak_model_name: gpt-4o-mini
use_repo_map: true
lazy: true
reminder: sys
逐项含义(ModelSettings 数据类定义见 aider/models.py):
| 参数 | 取值 | 作用 |
|---|---|---|
edit_format |
udiff |
默认要求模型以 unified diff 格式输出编辑。前文基准表明,diff 类格式对抑制“懒惰编码”有正面作用 |
weak_model_name |
gpt-4o-mini |
指定用于文件选择、commit message 等轻量任务的副模型 |
use_repo_map |
true |
在上下文预算内附加代码库的结构地图(repo map) |
lazy |
true |
标记该模型有“懒惰”倾向,触发 anti-lazy 提醒提示词 |
reminder |
sys |
行为提醒以 system 消息形式注入 |
注意 gpt-4-1106-preview 的配置块(第 103–108 行)与它几乎一致(同为 udiff + lazy: true + use_repo_map: true),差别在于新模型没有 examples_as_sys_msg 等附加项——从配置结构看,aider 对新模型沿用了针对“懒惰”模型的标准对策组合。
3. “anti-lazy”机制:lazy 标志如何变成提示词
lazy: true 这个配置项不是摆设,它在运行时会被翻译成追加进对话的行为提醒。在 aider/coders/base_coder.py 中:
if self.main_model.lazy:
final_reminders.append(self.gpt_prompts.lazy_prompt)
即:只要主模型被标记为 lazy,aider 就会在发送给模型的最终消息末尾追加 lazy_prompt。该提示词定义在 aider/coders/base_prompts.py:
lazy_prompt = """You are diligent and tireless!
You NEVER leave comments describing code without implementing it!
You always COMPLETELY IMPLEMENT the needed code!
"""
这直接呼应了原文对“懒惰编码”的刻画——提示词逐条针对“留下注释却不实现代码”这一行为。也就是说,即便你用 --model gpt-4-turbo-2024-04-09 运行,aider 也会在每次回复时提醒模型“勤勤恳恳、绝不留 TODO 注释、必须完整实现”。
4. 版本支持记录
HISTORY.md 中明确记录了这一支持:“Added support for new gpt-4-turbo-2024-04-09 and gpt-4-turbo models.”(对应条目同样出现在 aider/website/HISTORY.md 中)。这说明该模型的支持是以独立版本发布的形式加入的,而非顺带改动。
关于默认模型选择的说明与演进
原文(2024 年 4 月)的结论是:aider 将继续使用 gpt-4-1106-preview 作为默认模型,因为它是“GPT-4 家族中迄今为止最强的 coder”。
需要注意的是仓库的当前状态:在现行 aider/models.py 中,DEFAULT_MODEL_NAME 已经演进为 "gpt-4o"。这符合原文隐含的策略——默认模型跟随“最强的 coder”持续更换,而不是钉死在某一代快照上。因此,若你在当前仓库版本上运行 aider:
- 想复现原文评测所用的模型,显式使用:
aider --model gpt-4-turbo-2024-04-09; - 使用
--model 4-turbo别名时,解析到的是gpt-4-1106-preview而非带 Vision 的新模型; - 不指定模型时,使用的是当前仓库默认模型,与 2024 年 4 月文章发布时的默认值(
gpt-4-1106-preview)已经不同。
小结
这篇评测文章给出的可操作结论可以归纳为三点:
- 代码编辑能力:
gpt-4-turbo-2024-04-09在 133 题 Exercism 基准上得 62%,为 GPT-4 家族最低,但相对 63%–66% 的差距较小,统计上未必显著; - 重构/长代码能力:在 89 任务 laziness 基准上仅得 34%,以明显差距成为 GPT-4 Turbo 系列中“最懒”的模型——“懒惰编码”是这一代模型的主要短板;
- 使用方式:aider 通过
OPENAI_MODELS注册该模型、通过 model-settings.yml 为其配置udiff编辑格式与lazy: true标记、通过 base_coder.py 注入lazy_prompt反懒惰提示词;别名4-turbo始终指向gpt-4-1106-preview,默认模型则随仓库演进(当前为gpt-4o)。
atomcodeClaude Code 的开源替代方案。连接任意大模型,编辑代码,运行命令,自动验证 — 全自动执行。用 Rust 构建,极致性能。 | An open-source alternative to Claude Code. Connect any LLM, edit code, run commands, and verify changes — autonomously. Built in Rust for speed. Get StartedRust0624
Hy4-previewHy4 preview 是由腾讯混元团队研发的新一代混合专家(MoE)旗舰模型。模型总参数量 770B,每个 token 激活 49B,主干共包含78层,第一层采用标准 FFN,其余 77 层均为 MoE 结构,每层包含 256 个路由专家与 1 个共享专家,每个 token 激活 top-8 路由专家及共享专家。主干之外原生内置 1 层 MTP(总参数量 10B,激活 0.7B)以支持投机解码。Python00
GLM-5.3GLM-5.3 与 GLM-5.2 使用相同的基座模型——所有提升均来自后训练。与 GLM-5.2 相比,它在复杂编程和长程任务上的表现显著提升。Jinja00
GLM-5.3-FlashGLM-5.3-Flash (320B-A18B),是GLM-5系列的首个原生多模态模型。320B总参数,能力超过GLM-5.2Jinja00
Spark-X2.5-4BSpark-X2.5-4B 旨在让强大的 AI 更实用、更高效、更易获得。在广泛日常任务中表现强劲,涵盖对话、写作、翻译、推理、编码、工具调用以及智能体工作流,并在同等规模的开源模型中取得领先成绩。Spark-X2.5 将面向效率的架构与最高 1M tokens 的原生上下文窗口相结合,并支持 200 多种语言。Python00
Spark-X2.5-1.7BSpark-X2.5-1.7B 旨在让强大的 AI 更加实用、高效且易于获取。这些模型在广泛的日常任务中表现出色,涵盖对话、写作、翻译、推理、编程、工具调用和智能体工作流,并在同等规模的开源模型中取得领先结果。Spark-X2.5 将面向效率的架构与最高 1M tokens 的原生上下文窗口相结合,并支持 200 多种语言。Python00
