ClarifyGPT:通过意图澄清实现基于LLM的代码生成

互联不一般哥 2024-03-16 20:46:46

ClarifyGPT: Empowering LLM-based Code Generation with Intention Clarification

Fangwen Mu, Lin Shi, Song Wang, Zhuohao Yu, Binquan Zhang, ChenXue Wang, Shichao Liu, and Qing Wang.

引用

Fangwen Mu, Lin Shi, Song Wang, Zhuohao Yu, Binquan Zhang, ChenXue Wang, Shichao Liu, and Qing Wang. 2023. ClarifyGPT: Empowering LLM-based Code Generation with Intention Clarification. 1, 1 (October 2023), 21 pages. https://doi.org/10.1145/nnnnnnn.nnnnnnn

论文:https://arxiv.org/abs/2310.10996

仓库:https://github.com/ClarifyGPT/ClarifyGPT

摘要

大型语言模型(LLMs),如ChatGPT,能根据提供的自然语言需求自动生成代码。然而,用户需求可能存在歧义或不足。为了解决这一问题,我们引入了ClarifyGPT框架。它通过识别模糊需求并提出有针对性澄清问题来增强代码生成。ClarifyGPT首先执行代码一致性检查,如果发现需求模糊,就提示LLM生成澄清问题。收到回复后,ClarifyGPT完善需求并生成最终代码。人工评估显示,ClarifyGPT将GPT-4在MBPP-sanitized上的性能从70.96%提升到80.80%。自动评估结果表明,ClarifyGPT可以显著提高代码生成性能,将GPT-4和ChatGPT在四个基准测试中的平均性能分别提升到了75.75%和67.22%。ClarifyGPT有望促进LLMs在实际开发环境中的应用。

1 引言

代码生成旨在产生满足自然语言需求表达的用户意图的代码片段。最近努力通过利用具有数十亿参数的大型语言模型(LLMs),如ChatGPT和CodeGen,来解决这一任务。LLMs将自然语言需求(即提示)作为输入,并输出相应的代码片段,在代码生成方面取得了显著进展。然而,在实际应用中,由于用户经验和观点的多样性,用户编写的需求可能存在歧义或不足是不可避免的。例如,“编写一个函数来对元素列表进行排序”这样的需求没有明确指定用户是否希望按升序还是降序对列表进行排序。基于当前的LLMs的代码生成方法缺乏澄清模糊需求的机制,即它们根据这些不明确的需求直接生成程序,而不考虑交互式澄清。

我们认为赋予LLMs自动询问澄清问题的能力对于提高代码生成的质量和效率是必要的。然而,要赋予LLMs这种能力却面临着一些挑战,主要有以下几点障碍。(1) 何时询问澄清问题?在实际开发环境中,存在着大量的需求,包括模糊的和明确的需求。如果不能集中精力只询问模糊的需求,就可能导致LLMs与用户之间在明确定义的需求上进行不必要的交互。这些不必要的交互反过来又会降低效率并损害用户体验。(2) 应该问什么澄清问题?澄清问题的质量也会影响代码生成的效率和性能。精确和有针对性的问题有助于用户清晰地表达他们的意图,确保获得的回答直接与需求中存在的歧义相关。模糊或广泛的问题会增加获取与主题无关或不相关回答的风险,可能阻碍LLMs理解用户意图。

在本文中,我们提出了一个名为ClarifyGPT的新颖框架,通过需求澄清来增强基于LLMs的代码生成。首先,我们采用了一个两步的代码一致性检查来决定何时询问澄清问题。我们的动机是观察到将清晰的需求提供给LLMs通常会导致生成行为一致的多样化代码片段,即在给定相同的测试输入时,这些不同的代码片段很可能会返回相同的输出。而当提供一个不清晰的需求时,LLMs可能会生成行为不同的多样化代码片段。最初,ClarifyGPT指导LLMs通过比较具有不同功能的代码解决方案来分析导致给定需求模糊的因素。随后,根据这一分析结果,它制定有针对性的澄清问题。通过比较这些不同的代码实现,可以很容易地识别出需求中的潜在歧义点。在检测到需求中的歧义点后,LLMs可以为它们生成有针对性的澄清问题。最后,ClarifyGPT根据生成的问题及其回答对原始需求进行了进一步的完善,并生成了最终的代码解决方案。

为了评估ClarifyGPT的有效性,我们首先将GPT-4整合到ClarifyGPT中。人工评估结果显示,ClarifyGPT将GPT-4在MBPP-sanitized上的性能(Pass@1)从70.96%提升到了80.8%,将ChatGPT在MBPP-ET上的性能(Pass@1)从51.52%提升到了60.19%。然后,我们使用两种最先进的LLMs(即GPT-4和ChatGPT)在四个基准测试(HumanEval、HumanEval-ET、MBPP-sanitized和MBPP-ET)上进行了全面的实验。结果表明,与默认的GPT-4相比,ClarifyGPT在四个基准测试上的平均改进为11.52%;与默认的ChatGPT相比,ClarifyGPT在四个基准测试上的平均改进为15.07%。我们的主要贡献概述如下:

框架:我们提出了一个名为ClarifyGPT的新颖框架,使LLMs能够检测模糊的需求并制定有针对性的澄清问题。ClarifyGPT根据澄清问题的答案对模糊的需求进行完善,并进一步生成代码解决方案。用户模拟:我们引入了一种用户模拟方法,用于产生高保真度的模拟回答,以便在不同的LLMs和基准测试上自动评估ClarifyGPT,消除了直接用户参与的必要性。评估:我们在四个广泛使用的基准测试上进行了广泛的实验,以展示ClarifyGPT在不同模型和基准测试上取得了实质性的改进。人工评估进一步确认了将ClarifyGPT应用于实际环境中的巨大潜力。数据:我们提供了公开可访问的数据集和源代码,以便复制我们的研究并将其应用于广泛的环境中。此外,我们采用了不同的预训练模型(例如ChatGPT)来进一步研究GAMMA的泛化能力。

图1:ClarifyGPT整体工作流程

2 方法

在本节中,我们介绍了ClarifyGPT,这是一个针对LLMs的代码生成框架。图1展示了ClarifyGPT的概述,它包括四个主要阶段:(1)测试输入生成,旨在通过使用提示技术和启发式突变为给定需求生成高质量的测试输入;(2)代码一致性检查,用于利用生成的测试输入进行一致性评估,然后识别模糊的需求;(3)基于推理的问题生成,重点是为识别的模糊需求生成有针对性的澄清问题,通过提示LLMs参与中间推理;(4)增强的代码生成,它将澄清问题及其反馈结合起来,根据完善的提示生成最终的代码解决方案。接下来,我们为ClarifyGPT中的每个阶段提供详细说明。

2.1 测试输入生成

图2 基于输入 的基本类型感知变异列表

在这一步中,ClarifyGPT旨在生成高质量的测试输入,以有效区分具有不同功能的代码解决方案。许多研究已经尝试利用LLMs进行单元测试用例生成,并展示了令人印象深刻的性能。与之前的工作一样,ClarifyGPT利用LLMs作为测试输入生成器,并通过采用两步方法(即种子输入初始化和类型感知变异)生成测试输入。具体而言,ClarifyGPT首先设计一个提示来指导LLMs创建一组种子输入。然后,它执行类型感知变异以生成大量新的输入。我们的见解是:一方面,由于LLMs具有强大的理解和推理能力,将它们用作测试输入生成器可以产生高质量的输入,即使在语义约束下仍然有效。传统的输入生成器通常面临确保遵守此类语义约束的挑战。另一方面,由于大型模型的查询速度和成本不受欢迎,LLMs不适合大量自动化测试生成。因此,我们利用基于启发式变异的方法来加速生成大量测试用例,确保稳定性和可靠性。

2.2 代码一致性检查

清晰的用户需求应该易于理解,不留下任何解释的余地,而模糊的用户需求可能会导致利益相关者以不同的方式进行解释。受此启发,我们做出一个假设,对于给定的需求,如果一个LLM生成了具有不同功能的大量代码解决方案,这意味着该需求可能导致LLM以不同的方式进行解释。因此,这样的需求需要进一步澄清和完善。基于这一假设,我们提出了一种简单但有效的方法来确定模糊需求。首先,我们将给定的需求输入LLM以采样n个代码解决方案。然后,这些代码解决方案与上一步生成的测试输入一起执行。我们获取这些程序的测试输出,并比较测试输出以检查它们是否相同。如果输出相同,ClarifyGPT认为这些代码解决方案对需求的解释方式相同,从而将需求识别为清晰的。在这种情况下,其中一个采样的代码将被输出为最终的代码解决方案。然而,如果输出不相同,ClarifyGPT认为LLM在生成代码解决方案时对这个需求有不同的理解,并将该需求标识为模糊的。对于这些模糊的需求,如图1所示,我们进行代码聚类,根据它们的测试输出将这些代码解决方案分成几组。随后,ClarifyGPT从每个组中随机选择一个代码解决方案,并将这些不一致的代码解决方案输入到下一个组件中以合成用于提问的提示。

2.3 基于推理的问题生成

有针对性的澄清问题有助于用户清晰表达他们的意图,确保所获得的回答直接与需求中的不清楚部分相关。模糊或宽泛的问题会增加偏离主题或无关的回答的风险,这可能会影响代码生成的性能。因此,在识别出模糊的需求后,赋予LLMs制定精确且有针对性的问题的能力变得至关重要。为了实现这一目标,我们设计了一个基于推理的提示,旨在引导LLMs首先审查导致需求模糊的因素,然后基于分析制定有针对性的问题。设计的提示如图3(b)所示,包括三部分:(1)说明,描述我们希望LLMs解决的任务(即澄清问题生成);(2)少量样本对<需求、不一致的解决方案、澄清问题>,这些样本对帮助LLMs理解和解决任务;(3)一个查询,包含用户需求及其代码解决方案,用于LLMs生成问题。

具体而言,ClarifyGPT构建提示,引导LLMs通过理解这些不一致的代码解决方案的功能和比较它们的差异来分析导致需求不清楚的因素。动机在于,在软件开发中,代码解决方案代表需求的具体实现。如果一个需求是模糊的,不同的开发者可能会有不同的解释,因此写出不同的代码。这些不一致的代码解决方案中的一些可能是错误的或与原始意图不符。通过比较这些不同的代码实现,可以轻松地识别需求中的潜在模糊点。在检测到需求中的模糊点后,LLMs继续基于检测结果生成有针对性的澄清问题。我们提出的提示与Chain of Thought (CoT)提示有类似的思想,它促使LLMs首先生成中间推理步骤(分析导致模糊性的因素),然后基于这些中间推理步骤生成最终结果(有针对性的澄清问题)。通过这种方式,ClarifyGPT鼓励LLMs执行“远期规划”,使它们能够更好地利用其推理和理解能力来提高生成问题的质量。

图3 ClarifyGPT中使用到的prompt细节展示

2.4 增强的代码生成

一旦捕获到用户的响应,ClarifyGPT 将它们与生成的问题结合起来,将原始需求细化为清晰的需求。具体而言,如图3(d)中的查询所示,我们将每个问题及其对应的答案配对创建为一个澄清项,然后将它们附加到文档字符串的末尾,形成细化后的需求。通过这种方式细化模糊的需求,我们可以保留原始需求中文档字符串的结构完整性,同时通过额外的澄清信息增强它。随后,我们使用细化后的需求构建提示,指导LLMs生成最终的代码解决方案。构建的提示也由三部分组成,即指示、一些演示和一个查询,如图3(d)所示。

3 实验评估

为了评估ClarifyGPT的有效性,我们进行了全面的实验。

RQ1相对于基线方法,当接收到真实用户反馈时,ClarifyGPT的表现如何?

实验设置。我们探究ClarifyGPT在真实世界场景中的表现,即当接收真实用户反馈时,ClarifyGPT能否比现有的代码生成基准方法实现更高的性能。具体而言,我们将ClarifyGPT应用于GPT-4模型。由于MBPP-ET基准与MBPP-sanitized共享相同的用户需求,我们仅将ClarifyGPT应用于基准的原始版本(即MBPP-sanitized),并使用它们各自的单元测试报告ClarifyGPT在这两个基准上的性能。ClarifyGPT首先将基准中每个问题的用户需求作为输入,并将其确定为模糊或清晰。然后,它为模糊需求生成澄清问题。总共,我们从MBPP-sanitized基准中获得了140个具有模糊需求的问题。每个问题的平均澄清问题数量为2.85个。我们为每个问题制作了三份相同的问卷,确保每个问题由三个不同的参与者评估。每份问卷包括三个元素:(1)问题的(模糊的)需求,描述问题的意图;(2)包含预期输入输出示例的单元测试用例,帮助参与者理解问题的意图;(3)生成的澄清问题,参与者需要回答。 我们招募了十名参与者,包括三名博士生、两名硕士生、两名高级研究人员和三名行业开发人员。他们中没有人是本文的合著者。所有参与者至少具有三年的Python开发经验,其中六人拥有超过五年的经验。参与者最初提供了任务描述和包含适当问题答案的示例问卷。完成培训后,我们将42个问题分配给每个参与者,并要求他们根据问卷提供的信息回答澄清问题。每个问题将由三名参与者解决。 我们收集参与者提供的答案,并将其输入到ClarifyGPT中生成最终的代码解决方案。如前所述,我们使用单元测试用例评估生成的代码在两个基准上的正确性。由于每个问题的澄清问题由三名参与者回答,我们报告Pass@1结果的平均值。

结果。ClarifyGPT与其他基线的性能比较结果如表2所示。红色数值表示与默认基线相比,ClarifyGPT的相对改进。 我们可以看到,ClarifyGPT(人工反馈)在所有四个基准上均实现了最高的性能。与默认基准相比,ClarifyGPT(人工反馈)在Pass@1指标方面表现优异,在MBPP-sanitized上增加了13.87%,在MBPP-ET上增加了16.83%。此外,与表现最佳的基线(即CoT或GPT-Engineer)相比,ClarifyGPT(人工反馈)在MBPP-sanitized上的Pass@1性能也提高了9.53%,在MBPP-ET上提高了9.52%。这主要是因为ClarifyGPT能够有效地识别模糊的需求并提出有针对性的澄清问题。用户通过回答这些问题轻松澄清他们的意图,从而促进了LLMs生成更正确的代码。这表明作为交互式代码生成框架的ClarifyGPT可以支持开发人员在真实世界的开发环境中编写代码。

表2:ClarifyGPT(人类反馈)和基线在两个代码生成基准上的Pass@1(%)。 红色数字表示相对于默认的ClarifyGPT的改进。

回答RQ1。在人类评估中,ClarifyGPT提高了GPT-4在MBPP-sanitized上的性能(Pass@1)从70.96%到80.8%;在MBPP-ET上的性能从51.52%提高到60.19%。相对改进平均达到15.35%,超过了基准线。

RQ2 ClarifyGPT在接收模拟用户反馈时与最先进的基线方法相比表现如何?

实验设计。由于涉及人类参与,评估交互式代码生成框架ClarifyGPT非常昂贵且难以复制。一个相对简单的解决方案是进行离线评估。然而,这限制了系统从一组预定义或标记的问题中选择澄清问题,这在实际开发环境中无法很好地转化。在这个RQ中,我们应用用户模拟评估方法来促进ClarifyGPT在各种LLM和基准上的自动化评估,消除了直接用户参与的必要性。

模拟用户反馈的最关键方面是确保创建的用户反馈与在相同环境中用户提供的实际反馈非常相似。低保真度的模拟可能导致ClarifyGPT收到在实际实践中难以遇到的反馈,从而产生误导性结果并影响我们对ClarifyGPT性能的评估。因此,我们提出了一种高保真度的用户模拟方法,利用LLM生成用户响应,通过为LLM提供澄清问题和基准测试案例。我们的关键洞察是,基准测试案例包含预期的输入输出示例,反映了用户所需的功能。赋予LLM这些先验知识有助于它们理解用户意图,并能够生成高保真度的模拟用户反馈。为了指导LLM解决这个任务,我们设计了一个提示(如图3所示),它也包括三个部分:(1)一个说明,描述我们希望LLM解决的任务(即模拟用户响应);(2)少量示例<需求,基准测试,澄清问题,答案>四元组,帮助LLM理解和解决任务;(3)一个查询,包含一个用户需求及其基准测试,用于为LLM生成模拟响应。

我们应用了三个基线(第4.5节)和我们的ClarifyGPT到两个SOTA LLMs(第4.2节)。我们在四个基准(第4.3节)上评估它们,并通过计算Pass@1指标(第4.4节)来比较它们的性能。为了公平比较,所有基线都采用了与我们的ClarifyGPT相同的实验设置。

表 3. ClarifyGPT (模拟反馈)和基线在四个代码生成基准上的通过率@1(%)。红色数字表示 ClarifyGPT(模拟反馈)与默认值相比的相对改进。

结果。表3展示了ClarifyGPT(模拟反馈)与其他基线在代码生成方面的比较结果。红色的值表示相对于默认基线的ClarifyGPT(模拟反馈)的改进。总的来说,ClarifyGPT(模拟反馈)可以显著提高代码生成的性能,在不同的LLM和数据集上均取得了增益。对于GPT-4模型,与默认基线相比,ClarifyGPT(模拟反馈)在Pass@1性能上表现出明显的改进,在HumanEval数据集上增加了11.34%,在HumanEval-ET上增加了10.35%,在MBPP-sanitized上增加了10.89%,在MBPP-ET上增加了13.49%。对于ChatGPT模型,与默认基线相比,ClarifyGPT(模拟反馈)在四个基准上的Pass@1性能分别提高了15.10%,13.12%,12.98%和19.07%。结果表明,ClarifyGPT通过赋予LLM自主生成澄清问题并根据用户反馈改进用户需求,帮助用户澄清其意图,从而提高代码生成性能。

我们还注意到,与最相关的基线(即GPT-Engineer)相比,相对于Pass@1指标,表现出了更好的性能,在四个基准上平均改进了11.45%,8.65%,6.95%和8.56%。我们将这些改进归因于我们的新颖技术,即模糊需求识别和澄清问题生成。对于每个用户需求提出澄清问题会导致不必要的LLM-人类交互,从而增加了用户的额外负担,并在产生与主题无关的问题时影响了代码生成性能。虽然ClarifyGPT可以通过进行代码一致性检查来有效识别模糊需求,而无需任何监督训练。不一致的代码片段被视为输入,帮助ClarifyGPT制定指导用户澄清模糊问题的有针对性问题。

此外,我们观察到ClarifyGPT(人类反馈)的性能略高于ClarifyGPT(模拟反馈)。这表明我们的用户模拟方法可能会生成不符合用户意图的用户响应。然而,这两种方法都可以显著提高代码生成的性能,并在不同的LLM和基准上实现一致的增益,证明了我们模拟方法评估结果的可靠性。

回答RQ2:ClarifyGPT(模拟反馈)将GPT-4在四个基准上的平均性能(Pass@1)从68.02%提高到75.75%,将ChatGPT在四个基准上的平均性能从58.55%提高到67.22%。它们的相对改进分别为11.52%和15.07%,平均改进为13.27%。

RQ3 在提示中的演示数量如何影响ClarifyGPT的性能?

实验设计。在这个RQ中,我们调查演示数量的增加或减少是否会影响ClarifyGPT(模拟反馈)在代码生成任务上的性能。具体来说,由于LLM的输入长度限制,我们将提示中的演示数量从零变化到三。然后,我们将这两个LLM应用于ClarifyGPT及其变体,并评估它们在四个基准上的性能。我们运行这些方法三次,并将平均Pass@1结果报告为最终结果。

结果。表4展示了ClarifyGPT及其变体之间性能的比较。 总体上,ClarifyGPT对提示中演示数量表现出了鲁棒性。当演示数量从零变化到三时,ClarifyGPT始终优于两个LLM和四个基准上的默认基线。 我们可以观察到,正如预期的那样,随着演示数量的增加,ClarifyGPT的性能也在提高。特别是对于ChatGPT,当提示中的演示数量从零增加到三时,ClarifyGPT在四个基准上的平均性能从59.77%增加到67.22%。对于GPT-4模型,ClarifyGPT的平均性能从68.59%增加到75.75%。这主要是因为更多的演示可以为LLM提供各种情况和信息,使它们更好地理解问题的背景和所需的解决方案。此外,LLM可以通过演示学习更好地泛化,即从已知演示推断出新情况的解决方案。这使LLM能够更好地适应不同的输入和需求。 我们还发现,ClarifyGPT在零示范设置中的性能比默认基线略有改善,而在一示范设置中的性能明显优于默认基线。我们将这种差异归因于在零示范设置中,ClarifyGPT预计在没有任何演示的情况下生成有意义的响应,这对于复杂任务(例如,要求LLM生成有针对性的澄清问题)可能特别具有挑战性。此外,零示范提示仅依赖于LLM的预训练知识和给定提示的措辞,这可能不提供足够的指导或约束,使LLM产生准确或上下文相关的响应。相比之下,一示范设置中ClarifyGPT的性能明显高于零示范设置,并且接近于三示范设置中ClarifyGPT的性能。这表明当只提供一个演示时,ClarifyGPT具有强大的泛化性能。我们认为在实际使用场景中,将ClarifyGPT用于一示范设置可以在效果和效率之间达到平衡。

表4 不同演示数量下ClarifyGPT的实验结果。红色数字表示相对于默认情况下ClarifyGPT在不同演示数量下的相对改进。

回答QR3。总的来说,ClarifyGPT对提示中的演示数量表现出了鲁棒性。将演示数量从零变化到三时,ClarifyGPT在两个LLM和四个基准上始终优于默认基线。

转述:何晨曦

0 阅读:12

互联不一般哥

简介:感谢大家的关注