基于现有的大语言模型技术途径,利用当前人们积累的软件工程数据,能否实现人们心目中的软件自动化?这是软件工程界和机器学习界共同关心的问题。本文对“基于大语言模型的代码生成的研究现状和存在问题”,特别是“程序语言和自然语言固有差异导致的问题”,以及“现有代码数据的质量、覆盖度问题”进行探讨,分享了个人认识和思考。
人类是否有机会实现软件自动化?十年前,在大数据热潮的顶峰,我曾问过类似的问题。2014年10月,在日本国立情报学研究所主办的湘南会议(NII Shonan Meeting)1上,我作为共同主席组织了一个主题为“Computational Intelligence for Software Engineering”的研讨会(Seminar No.53)。会上我作了一个题为“Can Big Data Bring Us New Opportunities for Software Automation?”的报告,讨论的主题是我长期从事的研究领域“软件工程”的追求目标,即“高效率地开发出高质量的软件”,而这个目标的终极形态便是“软件自动化”。
软件自动化(根据需求规约自动生成程序)一直是计算机科学家们的梦想,今天仍然如此。我国软件界的先驱、南京大学徐家福先生曾给出“软件自动化”的定义:“软件自动化的广义理解指的是,尽可能借助计算机系统,实现软件开发。”其中,“软件开发指的是,从问题的非形式描述,经形式的软件功能规格说明、设计规格说明,到可执行的程序代码、调试,及至确认、交付使用的全过程。”同时,徐先生也给出了“软件自动化”的狭义理解,指的是“从形式的软件功能规格说明到可执行的程序代码这一过程的自动化”。
历史上,曾有很多研究人员为软件自动化这一目标付出努力,也取得了一些令人兴奋的成果,例如,编译器和词法分析器生成、声明式语言、程序综合、领域特定的编程、模型驱动的体系结构,等等。这些研究几乎都是采用基于“规则”的技术路径,虽然也取得了许多重要的学术成果,但仍未寻找到普遍适用于软件开发的自动化方法。这些工作所能合成的程序的规模依然较小,通常只能在有限的场景下(或狭窄的领域)实现程序的自动合成,而要合成真正实用的大型程序,仍极具挑战性。
大数据热潮的兴起,源于人们意识到,大数据为我们认识复杂系统带来了一种新思维和新手段。当时,无论是从科学研究还是商业应用视角,大数据应用在众多行业领域均已取得令人瞩目的成效。鉴于软件产业几十年的快速发展,特别是开源软件的蓬勃发展,我们已经积累了海量的软件工程大数据(包括代码、文档、注释、配置信息、错误报告等),一个自然的问题是:“可否发展出一种数据驱动的方法,自动地合成满足实际需求的大型程序”?
我在湘南会议报告的目的是提出这个问题供与会者讨论,也为解决这个问题探讨一下可能的路径。我在报告中针对该问题设计了两个场景:“单个功能代码的添加”和“多个功能代码的组合”。进而,考虑从前一个场景起步,针对若干特定领域,构建包含足够相似项目的多个版本的代码和需求文档的库,并基于该库将符合某个功能描述的代码自动添加到同领域的被开发系统中。
应该说,我在报告中并未明确回答我自己提出的问题,只是隐含了我的一个基本判断:基于软件工程大数据,不可能实现软件自动化的愿望,但有可能极大提升软件开发的效率和质量,也即是说,提供软件开发的“银弹2”。ACM图灵奖获得者、《人月神话》的作者弗雷德里克·布鲁克斯(Frederick Brooks)是在软件工程领域引入“银弹”概念的第一人。1987年,布鲁克斯曾预言:由于软件本质上的复杂性,未来十年内,不存在一种技术或方法能够使软件生产力得到10倍的提升;1995年,布鲁克斯在其著作《人月神话》新版中再次预言:“软件开发没有银弹的预言在下一个十年中仍然成立。”在软件工程发展历史上,曾有不少人希望发展出能作为“银弹”的软件开发方法和技术,如计算机辅助软件工程(Computer Aided Software Engineering, CASE)环境、面向对象(Object Oriented, OO)方法等均曾被寄予厚望,然而它们最终都没能成为真正的“银弹”。也许,“软件工程大数据驱动的方法”有可能成为“银弹”!这是当时我在报告中隐含的判断,更是一个期望。
“软件”一词自1960年前后出现以来,逐步成为计算机学科的一个主要研究分支。1968年“软件工程”一词诞生,软件在各行各业日益得到广泛的应用。在一定意义上,软件人已经利用“软件”帮助众多行业领域实现了行业业务的“自动化”,但是,“软件”自身的开发却一直采用手工方式,软件工程领域始终面临着“鞋匠的孩子没鞋穿”的窘境。实际上,这也是20世纪80年代CASE环境出现的动因之一。迄今,软件人还在为实现自动编程或软件自动化而持续奋斗中!
时至今日,站在当下的视角,我对湘南会议的报告也有一些反思:总体上,当时的判断趋于保守,低估了“大数据”叠加“深度学习”的威力。同时,鉴于当时大数据和人工智能技术所处的发展状态,跨界思维不够,主要是从软件工程的视角看待问题,特别是所设想的场景和起点高度依赖于“库”的工程可行性。
在历史上,围绕软件自动化这一主题,北京大学曾开展了一系列研究工作,包括杨芙清院士领导的“青鸟工程”,我领衔的国家973计划项目开展的“网构软件”(Internetware)3研究,以及我提出的“基于体系结构、面向构件的软件开发方法ABC”等,其目标都是希望通过自动化手段提升软件开发的效率和质量。自2014年开始,北京大学软件工程研究所李戈团队开始进入基于深度学习的程序处理领域,发布/发表了该领域最早的一批学术论文,在基于深度学习的程序理解、生成,以及面向程序处理的预训练模型等领域,做出了多项原创性贡献。2017年起,该团队持续研发了一个基于深度学习的编码辅助系统aiXcoder,以生成或补全程序代码的方式辅助程序员完成编程任务。当前,该系统逐步演化为基于大语言模型的编程辅助工具。
随着人们关于大语言模型研究的进展和应用的探索,“基于大语言模型的代码生成”成为人们关心的话题,我也一直关心相关研究和应用的进展。恰逢今年的中国计算机大会(CNCC2024)在浙江横店举行,CNCC程序委员会主席胡振江教授邀请我作个大会报告,更为机缘巧合的是,胡振江也是NII湘南会议的发起人,于是,我决定重用十年前的题目,只是将“大数据”换成了“大语言模型”。实际上,这也是一个自然的延伸,因为“大语言模型=大语料数据+深度学习”。报告中,我重点对“基于大语言模型的代码生成的研究现状和存在的问题”,特别是“程序语言和自然语言固有差异导致的问题”,以及“现有代码数据的质量问题、覆盖度问题”等话题进行探讨,并分享若干个人的认识和思考。
大模型应用远未达到应用繁荣期
当前,由于技术发展状态和应用环境的限制,大语言模型的应用领域严重受限,当然,也有代码生成、图像/视频生成等少数领域被认为“具有商用潜力”,甚至成为很多模型厂商看好的应用落地的优先选项。但是,图像/视频生成的应用仍限于交互增强、文生图像/视频等方面,并且在技术原理上遇到了“如何符合物理规律”的挑战;基于大语言模型的代码生成,则面临着“如何进行本地部署”等一系列挑战。
机器学习界和软件工程界视角不同
机器学习界当前的研究工作往往局限于“独立小程序”的生成,这一点从其研究工作所依赖的数据集的特征即可看出。机器学习界所使用的数据集通常具有以下特征:程序代码规模较小、代码依赖关系相对简单、编程需求的描述相对简单、对背景知识依赖较少、生成的代码缺乏或仅存在简单的上下文依赖、测试数据的规模较小、对生成结果的评估多借用自然语言处理领域的技术指标。
软件工程界的研究工作,则更多结合具体软件工程任务展开。相关研究工作通常有以下特征:数据采集自实际软件工程项目、代码规模相对较大、注重代码间的依赖关系、结合具体的软件开发任务(如代码补全、测试案例生成、代码注释生成等)、评估方式更多借鉴传统软件工程任务的评估方式(如测试案例通过率、代码覆盖度等)、注意观察和调研在实际软件开发项目中的应用效果。当然,需要指出的是,虽然软件工程界所关注的问题规模大于机器学习界,但与实际软件开发项目的规模相比,仍然较小,离实用仍有较大距离。
在机器学习界,一个常用的代码生成评估数据集是HumanEval,虽然研究者已经将该数据集上的Pass@1数值推升至超过90%,但如果我们仅仅给每个测试案例增加几个测试数据,其准确率就会大幅降低。而且,有些大模型为追求评估数据集上的准确率,还会进行有针对性的训练,从而造成了人们对代码生成准确率认知的偏差。而在软件工程界,研究者更倾向于利用一些来自真实开发项目的数据集进行测试,例如在北京大学推出的DevEval数据集中,GPT-4的Pass@1数值仅为53.05%,而在复旦大学推出的ClassEval数据集中,GPT-4的 Pass@1数值仅为37.6%。
关于代码生成在软件开发中应用的讨论
2024年5月,由StackOverflow网站发起的一个关于代码生成工具应用情况的调查中,针对6万个开发者的调查显示:76%的开发者表示正在或计划采用AI工具,81%的开发者认为 AI工具提升了开发效率;同时,也展现出开发者对AI工具的一些担心:仅有2.7%的开发者对AI工具的准确性有较高信心,45%的开发者认为A工具无法解决复杂问题;此外,70%的开发者认为AI工具不会对他们的工作造成威胁,79%的开发者认为“虚假信息”是他们担心的重要问题。
2024年4月,开源操作系统Gentoo Linux理事会发出了第一个关于“AI生成代码”的禁令,其考虑的主要因素包括版权、质量、道德等方面的问题。该理事会成员提出:“鉴于最近人工智能泡沫的蔓延,……目前唯一合理的行动是完全安全地禁止AI支持的贡献。……应明确禁止开发者使用ChatGPT、GitHub Copilot等创建在Gentoo中使用的代码、文档、消息、错误报告等。”最终,该理事会以6赞成票对0反对票通过了禁令。
国内软件工程界的观点
应该说,当前基于大语言模型的代码生成应用已经取得了不少进展,但距离人们的期待仍存在较大差距。原因可归为两个方面:程序语言代码的建模问题和构建大模型的数据问题。
现有大语言模型是否有利于程序语言代码的处理?
1.丢失了代码的强结构化特性。当前的大语言模型将代码视为文本字符串,并利用与自然语言相同的方式进行建模,忽略了代码的强结构化特性,丢失了程序语言不同成分之间的关联性和明确的约束关系。
2.丢失了代码的严格形式定义。编程语言可以利用语法产生式进行严格定义,编写代码的过程是在一个受限的形式化语法空间中描述程序语义的过程,而在现有大语言模型的建模过程中并未充分考虑程序语言的这一特性。
3.忽略了代码语义的强局部性。程序代码具有强局部性,程序语义通常被约束在局部空间中,诸多语言成分仅在受限的上下文环境中才具备特定的语义。例如,程序代码中相同的变量名,在不同的环境中可能具有不同的含义;而不同的变量名称,在不同的环境中可能具有相同的语义。程序语言代码的语义对局部环境的依赖远强于自然语言文本。
现有代码数据是否足以支持大模型训练?
首先,当前能够用于大模型训练的可用代码数据,无论从数量上还是质量上,都远远不足以支持建立一个可以用于实际软件开发的通用大模型。虽然互联网上的开源代码数据不断增长,但从中能够合法提取到的高质量代码数据仍然不多。例如,Github上的“公开代码库”按每年22%的速率增长,但迄今总数仍不超过300M。经互联网软件资产收录机构Software Heritage收录的代码文件数到目前为止仅有20B+,而且经过筛选、去重处理后,最终能够用于训练的代码仅占所收集原始代码数据的一小部分。根据华盛顿大学、苹果公司等23家研究机构和公司最近发布的研究论文DataComp-LM中的统计,最终用于训练的代码数据仅占原始数据的1.4%。
其次,面向不同特定行业领域的代码数据的可用性差距巨大。当前的大语言模型主要利用互联网上的公有代码数据进行训练,无法覆盖特定行业领域的私域数据。利用公开代码数据训练的模型,通常仅能支持通用领域的软件开发,然而,更多的软件开发需求来源于特定行业领域,需要支持特定的业务逻辑,利用公开代码数据训练的大语言模型无法充分支持特定行业领域的软件开发需求。
近期的研究数据也说明了大语言模型在“通用孤立小程序”与“领域工程项目”测评数据上的差异。例如,对于GPT-3.5而言,虽然其在HumanEval数据集上的BLEU(Bilingual Evaluation Understudy)值可以达到39%,但在领域相关的数据集上,该值却降低至5%,甚至更低。
这些问题的存在,影响了人们对大语言模型在代码生成领域应用的信心,也让我们意识到,大语言模型用于代码生成,其能力仍存在较大提升空间。
不能重新从数据起步,忘了我们已有的知识积累
人们在长期的软件技术研究和软件开发实践中,积累了大量的编程规则和关于软件开发的知识。我们不应抛弃这些积累,更不应该完全回到从原始数据中重新学习。当前大语言模型以自然语言文本为主要建模对象,并未考虑编程语言代码的特点,丢失和忽略了程序代码中蕴含的诸多信息。我认为以这样的方式处理和生成程序代码并不合适,我们应重视软件工程领域已有知识和规则的利用,将大语言模型与已有的软件工程技术和知识结合起来,以更好地解决问题。例如,把模型生成与程序代码的语法规则、编程规则结合起来,提升生成代码的正确性和稳定性;把模型生成与程序代码分析技术结合起来,提升生成代码的可靠性;把模型生成与软件领域知识结合起来,提升生成代码的领域适用性;把模型生成与形式化方法等技术结合起来,提升生成代码的可信性。
生成代码不等于生成软件
软件工程过程是一个涉及很多工序的复杂过程,包含了需求获取/分析、系统设计、开发、测试、运维等众多复杂任务,编码只是其中一个环节。研究表明,在实际的软件开发任务中,编码工作仅占全部工作时间的10%左右。而且,在软件工程过程中,相较于其他工作,编码是一类相对简单的工作。20世纪70年代,日本就曾提出“软件工厂”的概念,其中涉及的“编程工作”被限定为“将软件设计转换为程序代码”的过程。当时,软件开发人才短缺,日本很多高中生毕业后,经过短时间的编程培训,就可以从事编程工作。编程工作在当时往往被看作一种“短工”性质的任务,是软件开发流程中的后端环节。相对于编程工作,他们更重视需求分析和系统设计等前端环节,而这些工作需要的技术和知识含量更高,需要依赖高端人才。
当前大语言模型仍难以实现理想中的软件自动化,但有望成为软件开发的“银弹”
十年前讨论大数据时,我曾认为数据驱动的技术路径有可能成为软件开发的“银弹”。现在看来,虽然大数据的确为软件开发提供了基础资源,但如果只依靠传统的数据处理方式,效率太低,难以满足需求。而深度学习提供了一种自动化的数据处理分析手段,效率得以大幅度提升,在有足够质量保障的前提下,有可能带来软件编码效率数量级的提升。换言之,大数据与深度学习二者的结合,有望成为软件开发的“银弹”。当然,我们还需要一个前提,即软件工程方法技术与深度学习技术充分融合,以尽可能提高基于大语言模型生成代码的可信性和可解释性。
软件承载人类文明,人类必须牢牢掌控
软件是人类文明的载体。首个商业Web浏览器网景(Netscape)的发明人马克·安德森(Marc Andreesen)曾说过:“软件正在吞噬世界。”C++语言发明人比雅尼·斯特劳斯特鲁普(Bjarne Stroustrup)也说过:“人类文明运行在软件之上。”软件界在描述未来时也常说:“未来将是一个软件定义的世界。”软件已成为人类社会经济生活不可或缺的基础设施,必须牢牢地掌控在人类手上!因此,软件开发的主动权也必须掌控在人类的手中!
(本文根据CNCC2024特邀报告整理而成)
尾注:
1 NII湘南会议是由日本国立情报学研究所发起的一个国际化系列学术研讨会,风格类似于Dagstuhl Seminars会议。
2 在欧洲民间传说及19世纪以来哥特小说风潮的影响下,银弹(silver bullet)往往被描绘成具有驱魔功效的武器,是针对狼人、吸血鬼等超自然怪物的特效武器。后来被比喻为具有极端有效性的解决方法,作为杀手锏、最强杀招、王牌等的代称。
3 2000年,笔者和南京大学吕建教授在联合申报国家973计划项目时提出的概念。2002年,我们获批了软件技术领域第一个973计划项目。
梅 宏
CCF会士、前理事长。中国科学院院士。北京大学教授。主要研究方向为系统软件、软件工程。meih@pku.edu.cn
CCF推荐
【精品文章】
点击“阅读原文”,加入CCF。