虞慧群,黃家杰,范貴生,2,刁旭煬
1(華東理工大學(xué) 計(jì)算機(jī)科學(xué)與工程系,上海200237)
2(上海市計(jì)算機(jī)軟件評測重點(diǎn)實(shí)驗(yàn)室,上海201112)
E-mail:yhq@ecust.edu.cn
隨著現(xiàn)代化軟件庫和工具的規(guī)模和復(fù)雜性不斷增長,集成開發(fā)環(huán)境(IDE)已成為現(xiàn)代軟件工程師的基本范例,因?yàn)镮DE提供了一系列有用的服務(wù)來加速軟件開發(fā),代碼完成已經(jīng)成為IDE的基本特征.它基于上下文中的現(xiàn)有代碼建議下一個(gè)可能的代碼token.有效的代碼完成可以通過消除拼寫錯(cuò)誤并從上下文中識別正確的參數(shù)來幫助軟件開發(fā)者減少一些不必要的錯(cuò)誤,同時(shí)能夠快速開發(fā)軟件.
現(xiàn)有的代碼完成很大程度上依賴于編譯時(shí)類型信息來預(yù)測下一個(gè)token[1].因此,它適用于靜態(tài)類型的語言,如C++,Java.但是對于現(xiàn)在廣泛使用的動態(tài)類型語言(如JavaScript和Python)來說,由于缺少類型信息,這也就限制了現(xiàn)有的代碼完成對于動態(tài)類型語言的支持.
為了使動態(tài)類型能夠進(jìn)行有效的代碼完成,有一些基于簡單的啟發(fā)式和專有術(shù)語頻率統(tǒng)計(jì)來進(jìn)行代碼完成[2].但是,這種方法在完成代碼時(shí)僅檢查源代碼中的有限數(shù)量的元素.因此,這種方法的有效性可能無法很好地?cái)U(kuò)展到大型程序.
同時(shí)Hindle,White,Bielik[3-5]將編程語言視為自然語言,使用遞歸神經(jīng)網(wǎng)絡(luò)(RNN)之類的神經(jīng)語言模型可以捕獲順序分布和深度語義.然而,這些標(biāo)準(zhǔn)的神經(jīng)語言模型受到所謂的隱藏狀態(tài)瓶頸的限制:關(guān)于當(dāng)前序列的所有信息被壓縮成固定大小的矢量,這就使得RNN難以處理遠(yuǎn)程依賴.
注意機(jī)制能夠解決遠(yuǎn)程依賴的問題,與RNN結(jié)合能夠在大量NLP任務(wù)上實(shí)現(xiàn)最先進(jìn)的性能[6].注意機(jī)制使用隱藏層來計(jì)算輸入序列中元素的分類分布,以反映其重要性權(quán)重.但是大多數(shù)注意機(jī)制的缺點(diǎn)是時(shí)間順序信息丟失.
Li等人結(jié)合LSTM和注意機(jī)制來進(jìn)行代碼完成任務(wù),此外還利用指針機(jī)制來解決OoV單詞問題,并取得了很好的效果[7].但是由于使用的是LSTM和注意機(jī)制同樣對于挖掘代碼的遠(yuǎn)程依賴存在限制以及丟失了時(shí)間順序信息.
受到定向自注意網(wǎng)絡(luò)(Directional Self-Attention Network,DiSAN)[8]的啟發(fā),考慮源代碼上下文中的遠(yuǎn)程依賴和體現(xiàn)代碼結(jié)構(gòu)的時(shí)間順序信息對于代碼完成任務(wù)的重要性.針對此,本文做出以下貢獻(xiàn):
1)使用了一種定向自注意機(jī)制(Directional Self-Attention,DiSA),捕捉AST表示的源代碼之間的時(shí)間順序信息進(jìn)而學(xué)習(xí)源代碼的結(jié)構(gòu)信息,以及代碼上下文的遠(yuǎn)距離的依賴關(guān)系;
2)提出了挖掘代碼依賴之間的模型,更好地用于預(yù)測token的任務(wù),學(xué)習(xí)從全局詞匯表或本地上下文中生成下一個(gè)單詞;
3)基于兩個(gè)基準(zhǔn)數(shù)據(jù)集(JavaScript和Python)上來評估本文構(gòu)建的模型.實(shí)驗(yàn)結(jié)果表明,在預(yù)測token的準(zhǔn)確率方面,分別在JavaScript數(shù)據(jù)集上提高了1%左右,在Python數(shù)據(jù)集上提高了8%左右,這顯示了本文提出的模型相比于現(xiàn)有技術(shù)的有效性和先進(jìn)性.
近年來有一些工作探討了統(tǒng)計(jì)學(xué)習(xí)和序列模型在代碼完成任務(wù)中的應(yīng)用,例如n-gram模型[1,3]和概率語法[2,5,9].最近,神經(jīng)網(wǎng)絡(luò)進(jìn)行源代碼建模變得非常流行[10].
Bhoopchand使用RNN的稀疏指針機(jī)制,預(yù)測Python源代碼中的標(biāo)識符[11].然而,它們的指針組件以Python源代碼中的標(biāo)識符為目標(biāo),而不是本文工作中的包含標(biāo)識符,類型,變量等的所有的語料.Subhasis探索基于學(xué)習(xí)的代碼推薦,基于神經(jīng)網(wǎng)絡(luò)的學(xué)習(xí)技術(shù)使用機(jī)器學(xué)習(xí)來學(xué)習(xí)代碼的結(jié)構(gòu)和模式[12],并沒有編寫語法規(guī)則,試圖利用學(xué)習(xí)方法自動學(xué)習(xí)這些規(guī)則和模式.
RNN之類的深度學(xué)習(xí)技術(shù)已經(jīng)在語言建模任務(wù)中實(shí)現(xiàn)了最先進(jìn)的結(jié)果[13].Nguyen等人使用DNN來構(gòu)建語言模型,設(shè)計(jì)了一個(gè)上下文合并方法,用于源代碼的句法和類型注釋,進(jìn)行源代碼分析[14].
特別地,Li等人結(jié)合LSTM和Attention機(jī)制來進(jìn)行代碼完成任務(wù),而且利用指針機(jī)制解決OoV單詞問題,并取得了很好的效果[7].然而LSTM存在限制使得其不能有效的挖掘遠(yuǎn)距離的依賴關(guān)系,同時(shí)注意機(jī)制存在時(shí)間順序丟失的問題.定向注意機(jī)制提出用于解決自然語言處理中的LSTM的遠(yuǎn)距離依賴關(guān)系問題,并取得非常好的效果[8].代碼之間的時(shí)間順序信息以及代碼之間的依賴信息對于代碼完成任務(wù)來說是非常有用的,本文使用定向自注意機(jī)制來挖掘代碼之間的依賴關(guān)系和時(shí)間順序信息,促進(jìn)智能化代碼開發(fā)的進(jìn)一步發(fā)展.
注意機(jī)制計(jì)算來自兩個(gè)來源的元素之間注意分?jǐn)?shù)[15,16].給定源序列x=[x1,x2,…,xn]的標(biāo)記嵌入和查詢q的向量表示,注意通過兼容性函數(shù)計(jì)算f(xi,q)計(jì)算xi和q之間的注意權(quán)重,反映了xi和q之間的依賴關(guān)系,進(jìn)而轉(zhuǎn)化成源x對q的重要性依賴的概率.轉(zhuǎn)換成如下公式:
(1)
p(z|x,q)=softmax(a)
(2)
f(xi,q)=wTσ(W(1)xi+W(2)q)
(3)
(4)
自注意力是注意機(jī)制的一個(gè)特例.它用來自源輸入本身的令牌嵌入xj替換q.它通過計(jì)算每對令牌xj和xj之間的注意力來關(guān)聯(lián)單個(gè)序列在不同位置的元素.它對于遠(yuǎn)程和本地依賴都非常具有表現(xiàn)力和靈活性.
Shen等人提出一種多維自注意[8],探索來自相同源x的xi和xj之間的依賴關(guān)系,并為每個(gè)元素生成上下文感知編碼.
f(xi,q)=WTσ(W(1)xi+W(2)q+b(1))+b
(5)
其中f(xi,q)∈Rde是一個(gè)長度與xi相同的向量,所有權(quán)重矩陣W,W(1),W(2)∈Rde×de.
f(xi,xj)=WTσ(W(1)xi+W(2)xj+b(1))+b
(6)
然后,計(jì)算每個(gè)特征k∈[de]的所有n個(gè)標(biāo)記的分類分布p(zk|x,q).
(7)
來自x的所有元素的自注意的輸出是s=[s1,s2,…,sn]∈Rde×n.
定向自注意機(jī)制(DiSA)在自注意塊中使用探索依賴性和時(shí)間順序的“Mask”形成多維自注意塊,以及用于組合注意塊的輸出和輸入的融合門,其結(jié)構(gòu)如圖1所示.
圖1 定向自注意機(jī)制結(jié)構(gòu)圖
將多維自注意應(yīng)用于輸入,并為輸入序列中的所有元素生成上下文感知矢量表示.將位置掩碼應(yīng)用于方程自注意輸出的上下文感知矢量,使注意力機(jī)制產(chǎn)生了方向性.
f(xi,xj)=c·tanh([W(1)xi+W(2)xj+b(1)]/c)+Mij1
(8)
通過掩碼容易地編碼諸如時(shí)間順序和依賴性解析的先前結(jié)構(gòu)知識,并且在生成的編碼中進(jìn)行探索.
為了自注意,使用掩碼將時(shí)間順序信息編碼到注意輸出中.使用兩個(gè)掩模,即前掩模Mfw和后掩模Mbw,
(9)
(10)
在前向掩碼Mfw中,后一個(gè)元素j只關(guān)注早期元素i,反之亦然.
給定輸入序列x和掩碼M,根據(jù)方程(8)計(jì)算f(x),并遵循多維自注意的標(biāo)準(zhǔn)過程來計(jì)算每個(gè)j∈[n]的概率矩陣Pj.s中的每個(gè)輸出sj的計(jì)算方法如公式(7)所示.
DiSA的最終輸出u∈Rde×n是通過組合Mask的多維自注意塊的輸出s和輸入x來獲得的.這產(chǎn)生了每個(gè)元素/令牌的時(shí)間順序編碼和上下文感知矢量表示.
本節(jié)首先介紹了如何將源代碼程序轉(zhuǎn)換成AST抽象語法樹的形式,根據(jù)抽象語法樹遍歷形成節(jié)點(diǎn)序列,再進(jìn)行模型構(gòu)建.如圖2所示,使用AST的終端節(jié)點(diǎn)和非終端節(jié)點(diǎn)的序列來進(jìn)行下一個(gè)終端或非終端的預(yù)測,并構(gòu)建模型.
圖2 模型架構(gòu)
無論是動態(tài)類型還是靜態(tài)類型,任何編程語言都有明確的上下文無關(guān)語法(CFG),可用于將源代碼解析為抽象語法樹(AST).而且AST可以很容易地轉(zhuǎn)換回源代碼.并且以AST形式處理程序是軟件工程(SE)中的典型實(shí)踐[7,17,18].因此在實(shí)驗(yàn)的語料庫中,參考Raychev,Liu,Li等人的AST編碼操作[2,7],將每個(gè)源程序都以抽象語法樹(AST)的形式表示.
在AST中,每個(gè)非葉節(jié)點(diǎn)對應(yīng)于CFG指定結(jié)構(gòu)信息中的非終端.例如圖3顯示了一個(gè)示例Python程序及其相應(yīng)的AST.在Python中,非終端可以是body,F(xiàn)or,Call等.每個(gè)葉節(jié)點(diǎn)對應(yīng)于CFG中的終端,終端有無限的可能性,它們可以是變量名,字符串或數(shù)字等等.
將程序的AST信息編碼為圖3的格式,可以看到每個(gè)程序?qū)?yīng)的AST節(jié)點(diǎn)包含兩個(gè)屬性:節(jié)點(diǎn)的類型和值.
對于每個(gè)葉節(jié)點(diǎn),“:”用作類型和值類型之間的分隔符.對于每個(gè)非葉節(jié)點(diǎn),對其附加一個(gè)特殊的EMPTY標(biāo)記作為其值.例如,圖3中的AST節(jié)點(diǎn)NamaLoad:n,其中NameLoad表示該節(jié)點(diǎn)的類型,n是節(jié)點(diǎn)的值.類型編碼程序結(jié)構(gòu),例如body,for,If等.在實(shí)驗(yàn)所用的的語料庫中,類型的數(shù)量相對較少(只有數(shù)百種),值可以是任何程序標(biāo)識符,文字,程序操作符等.
圖3 Python源代碼轉(zhuǎn)換成抽象語法樹(AST)
將程序表示為AST而不是純文本能夠預(yù)測程序的結(jié)構(gòu),即每個(gè)AST節(jié)點(diǎn)的類型.通過這種方式,成功預(yù)測下一個(gè)AST節(jié)點(diǎn)不僅可以完成下一個(gè)令牌,還可以完成整個(gè)代碼塊.這種結(jié)構(gòu)使得能夠在不同粒度級別上更靈活地完成代碼.
給定部分AST作為輸入,將下一個(gè)非終端預(yù)測的輸入視為長度為K的序列,即(N1,T1),(N2,T2),……,(Nk,Tk).這里,對于每個(gè)i,Ni是非終端,并且Ti是Ni的終端值.對于每個(gè)非終端節(jié)點(diǎn)Ni,不僅編碼其種類,而且編碼非終端是否具有至少一個(gè)非終端子節(jié)點(diǎn).在這樣做時(shí),可以從輸入序列重建原始AST.將序列中的每個(gè)元素(例如,(Ni,Ti))稱為標(biāo)記.如上所述,沒有值的非終端被認(rèn)為具有EMPTY值.
該輸入序列(N1,T1),(N2,T2),……,(Nk,Tk)是所有問題的唯一輸入.在整個(gè)討論的其余部分中,將對Nk和Tk都使用embed編碼,并且非終端和終端的詞匯集是分開的.
本文中使用3.2節(jié)中提出的自注意機(jī)制公式(6)來挖掘源代碼輸入序列的(N1,T1),(N2,T2),……,(Nk,Tk)的每一個(gè)單詞對之間的自注意機(jī)制的注意的分?jǐn)?shù)f(xi,xj),通過這個(gè)注意分?jǐn)?shù)來展示出源代碼上下文中的代碼與代碼之間的注意力的權(quán)重,也就顯示出源代碼上下文中的代碼之間的依賴關(guān)系.
通過使用3.3節(jié)中的定向的自注意機(jī)制公式(8)將源代碼之間的時(shí)間順序與之前源代碼依賴關(guān)系結(jié)合起來,挖掘出源代碼的時(shí)間順序信息,進(jìn)而挖掘出程序代碼的結(jié)構(gòu)信息,同時(shí)挖掘出上下文之間的遠(yuǎn)程依賴關(guān)系.這里挖掘時(shí)間順序信息是挖掘出源代碼前向時(shí)間順序信息及其依賴關(guān)系ubw∈Rde×k和后向的時(shí)間順序信息及其依賴關(guān)系ubw∈Rde×k.
最后將前向自注意輸出與后向自注意輸出進(jìn)行結(jié)合uc∈R2de×k,通過對uc使用softmax進(jìn)行輸出的預(yù)測概率.
(11)
本文在兩個(gè)基準(zhǔn)數(shù)據(jù)集(1)http://plml.ethz.ch上評估了不同的方法:JavaScript(JS)和Python(PY),它們總結(jié)在表1中.從GitHub收集,兩個(gè)數(shù)據(jù)集都是公開可用的并用于以前的工作[2,5,7],兩個(gè)數(shù)據(jù)集都包含150,000個(gè)程序文件,這些文件以相應(yīng)的AST格式存儲,其中前100,000個(gè)用于訓(xùn)練,剩下的50,000個(gè)用于測試.在深度優(yōu)先遍歷中序列化每個(gè)AST之后,生成多個(gè)用于訓(xùn)練和評估的查詢,每個(gè)AST節(jié)點(diǎn)一個(gè),通過從序列中刪除節(jié)點(diǎn)(加上右邊的所有節(jié)點(diǎn)),然后嘗試預(yù)測節(jié)點(diǎn).
表1 實(shí)驗(yàn)數(shù)據(jù)集分析
Table 1 DataSet analysis
JSPYTraining Queries10.7×1076.2×107Test Queries5.3×1073.0×107Type Vocabulary95330Value Vocabulary2.6×1063.4×107
JS和PY中節(jié)點(diǎn)類型的數(shù)量最初為44和181.通過添加其有關(guān)子節(jié)點(diǎn)和兄弟節(jié)點(diǎn)的信息,將數(shù)字分別增加到95和330.如表1所示,兩個(gè)數(shù)據(jù)集中的節(jié)點(diǎn)值的數(shù)量太大而不能直接應(yīng)用神經(jīng)語言模型,因此僅在每個(gè)訓(xùn)練集中選擇K個(gè)最頻繁的值來構(gòu)建全局詞匯表,其中K是自由參數(shù).并且添加了三個(gè)特殊值:UNK用于表示詞匯外值,EOF表示每個(gè)程序的結(jié)束,和EMPTY表示AST中非葉節(jié)點(diǎn)的值.
實(shí)驗(yàn)設(shè)置為了與Li[7]等人的實(shí)驗(yàn)具有相當(dāng)?shù)目杀容^性,在本問的模型參數(shù)設(shè)置中,隱藏單元大小設(shè)置為1500.為了訓(xùn)練模型,使用交叉熵?fù)p失函數(shù)和mini-batch SGD與Adam優(yōu)化器[19].將初始學(xué)習(xí)率設(shè)置為0.001,并在每個(gè)時(shí)期后乘以0.6來衰減它.將漸變的范數(shù)設(shè)置為5以防止?jié)u變爆炸.批量大小為64,將模型訓(xùn)練8輪.每個(gè)實(shí)驗(yàn)運(yùn)行三次,并計(jì)算平均結(jié)果.
將每個(gè)程序劃分為由50個(gè)連續(xù)AST節(jié)點(diǎn)組成的段,如果未滿,則最后一段用EOF填充.所有其他變量使用[-0.05,0.05]上的均勻分布隨機(jī)初始化.使用準(zhǔn)確度作為實(shí)驗(yàn)的評估度量,即正確預(yù)測的下一個(gè)節(jié)點(diǎn)類型/值的比例.
預(yù)處理和訓(xùn)練細(xì)節(jié)由于每個(gè)AST節(jié)點(diǎn)由一個(gè)類型和一個(gè)值組成,要對節(jié)點(diǎn)進(jìn)行編碼并將其輸入到DiSA,分別為每種類型(300維)和值(1200維)訓(xùn)練嵌入向量,然后將兩個(gè)嵌入連接成一個(gè)向量.由于兩個(gè)數(shù)據(jù)集中類型的數(shù)量相對較少,因此在預(yù)測下一個(gè)AST節(jié)點(diǎn)類型時(shí)沒有未知單詞問題.
對于每個(gè)數(shù)據(jù)集,將訓(xùn)練集中具有K個(gè)最頻繁的節(jié)點(diǎn)值的AST節(jié)點(diǎn)值構(gòu)建全局詞匯表,并將訓(xùn)練集和測試集中的所有詞典外節(jié)點(diǎn)值標(biāo)記為OoV值.對于詞匯表內(nèi)的值,將它們標(biāo)記為全局詞匯表中的相應(yīng)ID.在訓(xùn)練期間,每當(dāng)訓(xùn)練查詢的基本事實(shí)是UNK時(shí),將該查詢的損失函數(shù)設(shè)置為零,以便模型不學(xué)習(xí)預(yù)測UNK.在訓(xùn)練和評估中,目標(biāo)值為UNK的所有預(yù)測都被視為錯(cuò)誤的預(yù)測,即降低整體準(zhǔn)確性.
對于每個(gè)實(shí)驗(yàn),本文運(yùn)行以下模型進(jìn)行比較,沒有任何注意或指針機(jī)制的標(biāo)準(zhǔn)LSTM網(wǎng)絡(luò);配備了注意機(jī)制LSTM網(wǎng)絡(luò);結(jié)合了注意力LSTM和指針網(wǎng)絡(luò)的混合網(wǎng)絡(luò);以及本文提出的使用定向自注意機(jī)制的模型;
5.3.1不同的K時(shí)預(yù)測終端節(jié)點(diǎn)值的準(zhǔn)確度
本文首先評估定向自注意模型在不同的頻繁的K個(gè)節(jié)點(diǎn)值對于預(yù)測下一個(gè)AST節(jié)點(diǎn)值,并與Li等人提出的指針網(wǎng)絡(luò)解決OoV單詞問題[7]進(jìn)行比較.對于兩個(gè)數(shù)據(jù)集中的每一個(gè),通過將節(jié)點(diǎn)值的全局詞匯量K改變?yōu)?K,10K和50K來創(chuàng)建三個(gè)特定數(shù)據(jù)集,從而導(dǎo)致不同的詞匯外(OoV)率.在每個(gè)特定數(shù)據(jù)集上運(yùn)行上述模型,表2列出了相應(yīng)的統(tǒng)計(jì)數(shù)據(jù)和實(shí)驗(yàn)結(jié)果.
表2 不同的K時(shí)預(yù)測下一終端節(jié)點(diǎn)值的準(zhǔn)確度
Table 2 Accuracy on next value prediction with different vocabulary sizes
Vocabulary SizeJS_1KJS_10KJS_50KPY_1KPY_10KPY_50KOoV Rate20%11%7%24%16%11%LSTM69.9%75.8%78.6%63.6%66.3%67.3%Attentional LSTM71.7%78.1%80.6%64.9%68.4%69.8%Pointer Mixture LSTM73.2%78.9%81.0%66.4%68.9%70.1%DiSA(Ours)72.8%79.5%82.5%69.6%74.6%76.7%
如表 2所示,在每個(gè)特定數(shù)據(jù)集中,vanilla LSTM實(shí)現(xiàn)了最低精度,而注意力LSTM提高了vanilla LSTM的性能,指針混合網(wǎng)絡(luò)實(shí)現(xiàn)了高精度,同時(shí)本文的定向自注意機(jī)制模型在5個(gè)實(shí)驗(yàn)上實(shí)現(xiàn)了最高精度.此外,還可以看到,通過增加JS或PY數(shù)據(jù)集中的詞匯量大小,OoV率降低,并且由于更多可用信息,不同模型的一般準(zhǔn)確度增加.
在JS數(shù)據(jù)集中K設(shè)置為1K時(shí),可以看到此時(shí)的OoV Rate在此時(shí)比較高,此時(shí)本文使用的模型預(yù)測的準(zhǔn)確率要比混合指針網(wǎng)絡(luò)預(yù)測的準(zhǔn)確率低0.4%,同時(shí)在PY數(shù)據(jù)集上同樣的K值并且OoV Rate更加高時(shí)本文提出的模型的預(yù)測準(zhǔn)確率要比混合指針網(wǎng)絡(luò)的效果要高3.2%左右,可以猜測混合指針網(wǎng)絡(luò)并沒有很好的挖掘到代碼的長程依賴和時(shí)間順序信息,同時(shí)可以注意到自注意機(jī)制的性能提升,并且增益是最大的,性能增益歸因于當(dāng)前代碼段的時(shí)間順序信息以及代碼之間的依賴關(guān)系.
從這部分實(shí)驗(yàn)結(jié)果說明,在沒有充分挖掘到代碼段的時(shí)間順序信息和代碼之間的依賴關(guān)系,考慮OoV單詞對于預(yù)測效果是沒有太大幫助的.從實(shí)驗(yàn)結(jié)果看出本文提出基于定向自注意機(jī)制的模型對于下一節(jié)點(diǎn)值的預(yù)測的準(zhǔn)確度都保持在最高準(zhǔn)確率,說明相比較配備了Attention機(jī)制的LSTM的混合指針網(wǎng)絡(luò)來說,本文提出的基于定向自注意機(jī)制的網(wǎng)絡(luò)模型能夠非常有效的挖掘到代碼之間的依賴關(guān)系和代碼段的時(shí)間順序信息進(jìn)而挖掘代碼段的結(jié)構(gòu)信息,并且時(shí)間順序信息所反映出的結(jié)構(gòu)信息和代碼之間的依賴關(guān)系對于下一個(gè)結(jié)點(diǎn)值的預(yù)測來說是非常有幫助的.
5.3.2 有效性比較
由于已經(jīng)有先前在兩個(gè)基準(zhǔn)數(shù)據(jù)集上進(jìn)行代碼完成的研究,為了驗(yàn)證提出的方法的有效性,需要與現(xiàn)有技術(shù)進(jìn)行比較.特別是,Liu等人在JS數(shù)據(jù)集上使用標(biāo)準(zhǔn)LSTM[6].Raychev等基于概率語法構(gòu)建了代碼的概率模型[2],以及Li 等提出并使用結(jié)合Attention機(jī)制的LSTM并結(jié)合指針網(wǎng)絡(luò)的混合網(wǎng)絡(luò),并在兩個(gè)數(shù)據(jù)集上實(shí)現(xiàn)了最先進(jìn)的代碼完成精度[7].
具體來說,分別對整個(gè)AST中的每一個(gè)AST節(jié)點(diǎn)類型(TYPE)預(yù)測和該結(jié)點(diǎn)對應(yīng)的節(jié)點(diǎn)值(VALUE)預(yù)測進(jìn)行實(shí)驗(yàn).將值詞匯量大小設(shè)置為50K,以使結(jié)果與當(dāng)前先進(jìn)的結(jié)果相當(dāng).結(jié)果如表3所示.
表3 有效性比較
Table 3 Comparisonofthe effectiveness
MethodsJSTYPEVALUEPYTYPEVALUELSTM88.1%78.6%79.3%67.3%Att-LSTM 88.6%80.6%80.6%69.8%PM-LSTM-81.0%-70.1%P-Model 83.9%82.9%76.3%69.2%DiSA(Ours)89.2%82.5%88.4%76.7%
表3顯示了本文所提方法與相關(guān)方法的實(shí)驗(yàn)效果對比.Pointer Mixture LSTM僅在兩個(gè)數(shù)據(jù)集上預(yù)測下一個(gè)值.對于下一個(gè)類型預(yù)測,其仍然使用的是具有Attention機(jī)制的LSTM,而本文提出的基于定向自注意機(jī)制的模型同時(shí)預(yù)測了下一個(gè)節(jié)點(diǎn)的類型和值,并且在兩個(gè)數(shù)據(jù)集上實(shí)現(xiàn)了最高精度,顯著提高了兩個(gè)數(shù)據(jù)集的最佳記錄.對于JS數(shù)據(jù)集的下一個(gè)值預(yù)測,本文提出的模型實(shí)現(xiàn)了與Probalilistic Model[2]相當(dāng)?shù)男阅?,這是一個(gè)基于特定領(lǐng)域語法的概率模型,但是在下一個(gè)類型預(yù)測,本文提出的模型顯著提高了預(yù)測精度.并且,本文提出的模型的結(jié)果優(yōu)于當(dāng)前比較先進(jìn)的幾個(gè)模型提出的結(jié)果.在PY數(shù)據(jù)集上,本文提出的模型用于下一個(gè)類型預(yù)測和下一個(gè)值預(yù)測的效果均要優(yōu)于先前的最佳記錄,顯著提高了預(yù)測精度.因此,可以得出結(jié)論,本文提出的基于定向自注意力機(jī)制網(wǎng)絡(luò)對于代碼完成是有效的,在四個(gè)任務(wù)中實(shí)現(xiàn)了三個(gè)最先進(jìn)的性能.
在本文中,將定向自注意機(jī)制應(yīng)用于代碼完成任務(wù),并開發(fā)一種關(guān)注程序AST的時(shí)間順序信息的注意機(jī)制.為了處理代碼完成中的節(jié)點(diǎn)值的預(yù)測,本文提出了一種使用定向自注意機(jī)制的網(wǎng)絡(luò),它有效挖掘代碼段當(dāng)前上下文的時(shí)間順序信息,以及源代碼上下文的代碼之間的依賴關(guān)系.實(shí)驗(yàn)結(jié)果表明了本文方法的有效性.