GraphCodeBert: Pre-Trainng Code Representions with Data Flow
创新点:认为AST中有许多不必要的联系且仅是在语法层面,而DFG关注了语义层面:采用数据图流向【将程序中变量作为图的节点,将变量之间的数据流向作为边,mask掉部分边后再进行预测】
三个预训练任务:MLM、EP边预测(即创新点)、NA节点对齐【将NL中的变量与PL中的变量进行对齐训练】
标题 | GraphCodeBert: 用数据流进行预训练代码表示 |
会议/期刊 | ICLR 2021 |
作者 | Daya Guo1∗, Shuo Ren2∗, Shuai Lu3∗, Zhangyin Feng4∗等 |
关键词 | 数据流 |
摘要 | GraphCodeBERT试图考虑代码的内在结构以提高对代码的理解和处理。
|
引言
程序语言预处理模型是受启发于自然语言与处理模型。预处理模型在程序语言处理任务上(如代码搜索、代码补全、代码摘要等等)取得了很好的成就,然而目前存在的预处理模型都是将代码视作token序列而忽略了代码的内在结构。本文作者基于此设计了GraphCodeBert这样一个考虑代码内在结构的预训练模型。 首先,为了融入代码结构,开发者并没有考虑AST(抽象语法树),而是采用了DFG(数据流向图)。他们认为AST代表的是各个token之间的句法关系,是syntactic层面的关系,而DFG代表的变量之间的来源关系,是semantic层面的关系。DFG在一定程的上能够避免AST中一些不必要的联系从而提升了模型的有效性; 其次,GraphCodeBert也是基于Transformer开发的; 最后,GraphCodeBert是通过三项预训练任务来训练模型的:MLM(掩语言模型)、EP(数据流向图的边预测)和NA(数据流向图节点和代码token之间的关系预测)。 GraphCodeBert是第一个加入语义级别的代码结构的预训练模型,并且提高了四个下游任务(代码搜索,克隆检测,代码翻译和代码改错)的处理能力。
数据流向图
数据流向图DFG是一个有向图,代表的是每个变量的值从哪里来到哪里去的关系。
下图代表了同一个python函数(功能是输入两个数,返回两数中较大的那个数)分别转换成AST和DFG后的结果。
模型
模型架构
输入序列
Transfomer
基于图的掩码注意力机制
预训练任务
同bert一样,GraphCodeBert也只训练编码器。GraphCodeBert通过MLM、EP和NA三个任务来训练编码器。
MLM 掩码语言模型
这个任务也是参考bert的训练工作从代码序列和注释序列中选取15%的token,其中80%会被掩盖,10%会替换成一个随机的token,剩下的10%不做变化。MLM的任务就是由扰乱后的序列输出扰乱之前的序列。
EP 边预测
加入这项任务是为了使得模型能够学习到data flow中的信息。
NA 节点对齐
下游任务
为了显示GraphCodebert的有效性,作者进行了四项下游任务,包括了:代码搜索、克隆检测、代码翻译和代码改错。
代码搜索
这个实验的任务是通过输入一段自然语言描述,模型输出从代码库中选出一段最符合描述的代码。这个实验所用的数据集为经过预处理之后的CodeSearchNet,并且以Mean Reciprocal Rank (MRR)作为评价标准。
实验结果对比
以上模型主要通过计算代码和查询描述之间的内积来对候选的代码进行排名的。第一组分别代表了词袋模型、卷积神经网络、双向RNN和自注意力机制;第二组代表的一些预训练模型,RoBerta是一个在文本语料库上通过MLM任务训练的模型,RoBerta(code)则是在代码上的预训练模型,CodeBert是在文本-代码对上通过MLM训练的模型。
克隆检测
任务的目的是给出两个输入代码的相似度。实验使用的数据集是BigCloneBench
实验结果对比
案例
上图显示了对于两个字面相似但是语义不同的函数 ,GraphCodeBert给出了正确的结果而其他两个模型预测错误。
代码翻译
代码翻译的任务就是能够将一种语言的代码转换成另一种语言。
实验结果对比
Navie是将源语言原封不动输出用来做参照;
PBSTMT代表的是以短语为基础的统计学机翻模型。
代码改错
实验结果对比
上图显示了不同模型分别在短和中等长度的代码中的能力评价。
模型分析
消融实验
对比去除任意一个组件在代码搜索任务上的表现:
注意力分布
[CLS]被认为是可以和一个输入序列中所有的token做注意力,因此[CLS]在一定程度上也代表了这个代码的表征向量。
上图第一行表示了代码和DFG节点的数量分布;第二行表示了[CLS]对于代码和节点的注意力分布。此图表说明了模型对于单个节点具有更高的注意力。
AST与DFG的对比
AST Pre-order Traversal通过先序遍历来序列化一个AST;AST Subtree Masking是一个transfomer模型,但是AST上的每一个节点只能注意到他的子代。
上图显示,当输入序列长度较低时,AST相关的模型的MMR评分低于参照,而无论输入长度如何GraphCodeBert表现效果都明显高于AST。作者给出的解释是:AST中包含了大量不必要的联系。
上图则显示了data flow的有效性,通过对比有没有dataflow这个结构的模型对自然语言描述和代码的匹配度。
模型局限
首先模型不能处理一些特有的库,如tensorflow;其次模型还会出现一些类似于标识符未定义先使用、括号没闭合等问题。
标签:Pre,Code,Trainng,训练,AST,代码,GraphCodeBert,任务,模型 From: https://blog.51cto.com/u_16341877/8181576