【复杂指令遵循 Benchmark】论文分享:CodeIF-Bench
论文名称:CodeIF-Bench: Evaluating Instruction-Following Capabilities of Large Language Models in Interactive Code Generation
论文链接:https://arxiv.org/abs/2503.22688
机构:北航 + 华为云
Github代码链接:https://github.com/zhu-zhu-ding/CodeIF-Bench
简介
现有代码生成的基准多关注单轮交互的功能正确性,缺乏对多轮交互中指令遵循能力的评估,尤其在复杂上下文和多轮对话场景下。所以本文提出了一个CodeIF-Bench,来对多轮代码生成任务中LLM的指令遵循能力进行自动化评估,而且任务覆盖不同难度等级,最高可达仓库级任务。
构造方法
框架概述
图2展示了CodeIF-Bench基准构建中可验证指令策略提取和数据收集的流程,具体如下:
- Step-1:VI Strategy Extraction(可验证指令策略提取 )
① Code Review Comment(代码评审评论 ):从实际的代码评审评论入手,这是整个流程的起始点。
② Clustering(聚类 ):对收集到的代码评审评论样本进行聚类,把相似的评论归在一起。比如“什么是polygamma的输出类型?”“allocation(888, 887)会发生什么?”等评论就是样本。
③ LLM Abstraction(LLM抽象 ):利用LLM对聚类后的评论进行处理,将其抽象成高级需求。像输出类型一致性、边界条件处理、版本兼容性检查等就属于高级需求。
④ Check(检查 ):由人工对LLM生成的高级需求进行检查,最终确定可验证指令策略,包括输入输出条件、边缘情况处理、异常处理、上下文使用验证等策略。
- Step-2:Data Collection(数据收集 )
① Data Source(数据源 ):数据来源于MBPP和DevEval 。这里会获取指令(包括功能描述、函数参数等 )、初始测试(如tests/test_socketutils.py:test_socketutils )以及项目信息(命名空间、项目路径等 )和依赖信息。
② Initial Instruction(初始指令 ):基于数据源生成初始指令,比如要求编写一个名为“setmaxsize”的Python函数,同时会给出函数功能和参数等信息,还可能包含黄金上下文(如boltons.socketutils.NetstringSocket的代码 )。
③ Verifiable Instruction Pool(可验证指令池 ):依据可验证指令策略,生成一系列可验证指令。例如针对“setmaxsize”函数,指令可以是函数应接受一个整数参数并相应更新实例属性,以及当参数不是正整数或零时应引发ValueError异常等。
④ Verifiable Instruction Tests(可验证指令测试 ):为每个可验证指令创建对应的测试用例,如tests/test_socketutils.py:test_setmaxsize_updates_attributes_on_invalid_maxsize等,用于验证生成的代码是否满足指令要求。
⑤ Interactive Session(交互会话 ):在交互过程中,先给出初始指令,LLM生成代码后进行初始测试;接着给出第一条可验证指令,模型生成对应代码后,结合初始测试和这条指令的测试进行验证;依此类推,不断加入新的可验证指令并进行测试,逐步完善和评估代码。
一句话总结就是:先从代码评审评论里找问题并分类,用LLM提炼成需求,确定验证策略,再结合现有案例明确初始指令,依策略生成具体指令和测试用例,在交互中不断完善来构造评测集。
下面介绍下Step-1和Step-2的一些处理细节。
VI Strategy Extraction(可验证指令策略提取 )
- 提取思路
软件开发中代码评审过程与程序员和LLM生成代码的交互过程相似,受此启发,从真实代码评审评论提取 VI 策略,为生成可验证指令提供指导。
- 提取步骤
① 用 KCenterGreedy 算法基于文本嵌入选出 500 个有代表性的代码评审评论候选样本。
② 让 GPT-4o 为每个候选评论生成 “高级需求” 策略。
③ 邀请 2 位有经验的软件工程专家检查策略,剔除不可验证类型、合并相似策略、细化模糊需求,最终得到 9 种 VI 策略,涵盖功能和非功能需求,其中 2 种与上下文相关 。
Data Collection(数据收集 )
- 任务采样
① 从 MBPP 和 DevEval 两个广泛使用的代码生成基准中采样 122 个编程任务,其中 50 个来自 MBPP(独立函数任务,L - 1 级别 ),72 个来自 DevEval(仓库级代码生成任务,涵盖 L-1、L-2、L-3 不同依赖类型 )。
② 从 DevEval 采样时,先从 115 个真实项目中随机选 100 个任务,覆盖 10 个领域和不同依赖类型,经人工评审剔除低质量任务后确定 72 个任务。
- 指令与测试生成
① 根据提取的指令策略为每个任务生成可验证指令(SA 任务 7 条,Non-SA 任务 9 条 ),并使用 GPT-4o 基于初始指令和指令策略生成(可验证指令,测试用例 )对。
② 之后由两位有 4 年以上 Python 编程经验的开发者检查和完善数据,通过执行测试解决错误和逻辑不一致问题。
- 基准特性
最终构建的 CodeIF - Bench 包含 122 个编程任务和 879 条可验证指令,其具有以下特性:
① 支持独立函数级和仓库级代码生成评估;
② 提供 9 种源于真实用户需求的可验证指令类型及对应测试用例;
③ 通过计算 pass@k 分数准确评估指令遵循能力和基础编程能力;
④ 支持多轮指令遵循能力评估,将无冲突的单轮指令组合成多轮对话并独立验证。
基本参数
任务难度分级
-
L-1:仅依赖内置函数和标准库(无上下文依赖)。
-
L-2:需要文件内上下文(如同一文件中的类或函数定义)。
-
L-3:需要跨文件上下文(如不同文件间的依赖关系)。
任务分类
-
SA级任务:指StandAlone(独立)编程任务 ,通常仅依赖内置函数和标准库,无上下文依赖,如一些简单的独立函数编写任务。
-
Non-SA级任务:即Non - StandAlone(非独立)编程任务 ,这类任务的指令需要借助特定上下文信息来完成,像涉及文件内或跨文件依赖的仓库级代码生成任务。
任务平均指令长度
表1显示了CodeIF-Bench包含122个编程任务(57.4%为独立任务L-1,42.6%为仓库级任务L-2/L-3),覆盖9种可验证指令,任务平均指令长度随上下文依赖复杂度(L-1至L-3)显著增加,其中L-3任务平均长度达28K tokens。
评估维度覆盖
表2显示,CodeIF-Bench是唯一在代码领域、真实代码场景、指令遵循评估、鲁棒指标及多轮支持五个维度均达标的基准,而现有其他代码生成或指令遵循基准均存在至少一项缺失。
评价指标
pass@k
其中,k为每条指令生成的程序数,c为通过测试的程序数,n为初始指令数量。
使用方法
详见Github的Readme,很详细,不赘述。目前最新的排行榜还是论文里面的表3,可以看到基本上所有模型应对L3级的项目级任务都跪了,任重道远啊。
总结
本文提出的这个评测集的重点在于怎么构建多轮中持续交互的问题,可以理解成从第n(n>1)轮开始的问题,都会从一个可验证的指令池子里面去抽取问题,来实现这个自动化的评估。
整体思路还是非常可以的,而且Github的Readme真得非常详细,需要的同学可以一试。