包盼盼,陶傳奇,2,3,4+,黃志球,2,4
1.南京航空航天大學(xué) 計算機(jī)科學(xué)與技術(shù)學(xué)院,南京210016
2.南京航空航天大學(xué) 高安全系統(tǒng)的軟件開發(fā)與驗(yàn)證技術(shù)工信部重點(diǎn)實(shí)驗(yàn)室,南京210016
3.南京大學(xué) 計算機(jī)軟件新技術(shù)國家重點(diǎn)實(shí)驗(yàn)室,南京210023
4.軟件新技術(shù)與產(chǎn)業(yè)化協(xié)同創(chuàng)新中心,南京210016
為了幫助開發(fā)人員進(jìn)行代碼復(fù)用,部分研究人員關(guān)注編程智能化相關(guān)的研究。比如,在代碼推薦中,Jiang 等人[1]將機(jī)器學(xué)習(xí)算法和傳統(tǒng)信息檢索方法結(jié)合進(jìn)行方法塊推薦,Gu 等人[2]利用深度學(xué)習(xí)方法進(jìn)行API(application programming interface)使用序列的推薦。但是,大部分編程智能化相關(guān)的研究都聚焦于各種算法的研究,而忽略了研究所使用數(shù)據(jù)的質(zhì)量問題。大部分相關(guān)研究中所使用的數(shù)據(jù)都來源于GitHub。GitHub 作為開源平臺,項(xiàng)目托管者可能來自正規(guī)組織或軟件公司(如Apache、Google 等),也有可能是新手開發(fā)者,由于開發(fā)者代碼編寫水平參差不齊,GitHub 上的項(xiàng)目并不能保證都具有較高質(zhì)量。根據(jù)“garbage in,garbage out”,源碼的數(shù)據(jù)質(zhì)量會對基于大規(guī)模源碼進(jìn)行智能化學(xué)習(xí)的結(jié)果質(zhì)量產(chǎn)生重要影響。
當(dāng)前對開源源碼數(shù)據(jù)進(jìn)行處理的工作主要關(guān)注數(shù)據(jù)的過濾、清洗等。比如,江賀等人在進(jìn)行方法塊推薦的相關(guān)研究時,對采集的數(shù)據(jù)進(jìn)行了篩選處理,包括刪除代碼行數(shù)少于5 行的代碼片段和刪除結(jié)果中可能重復(fù)的方法塊。但是,鑒于源碼數(shù)據(jù)的復(fù)雜性[3],簡單處理較難滿足研究人員對代碼數(shù)據(jù)質(zhì)量的要求。結(jié)合傳統(tǒng)的數(shù)據(jù)清洗相關(guān)研究可以發(fā)現(xiàn),方法塊的冗余清除屬于重復(fù)對象檢測,僅僅是數(shù)據(jù)清洗研究內(nèi)容的一方面。代碼數(shù)據(jù)集作為智能化編程系統(tǒng)研究的基礎(chǔ),其數(shù)據(jù)質(zhì)量的問題還缺乏相關(guān)的研究。
針對上述問題,本文對已有的開源數(shù)據(jù)托管平臺上的海量源碼數(shù)據(jù)進(jìn)行綜合分析,從不同的維度對源碼數(shù)據(jù)質(zhì)量進(jìn)行評估,并建立一種面向開源源碼大數(shù)據(jù)的質(zhì)量分析方法。本文工作的主要貢獻(xiàn)在于,考慮到已有研究工作的困難和不足,研究回答了以下兩個重要問題:
(1)開源項(xiàng)目托管平臺上的源碼數(shù)據(jù)可能存在哪些質(zhì)量問題。
(2)如何利用定性或定量的方式對開源代碼數(shù)據(jù)質(zhì)量進(jìn)行評估。
本文以國際通用的開源軟件代碼庫GitHub 中的開源項(xiàng)目作為代碼數(shù)據(jù)質(zhì)量問題的研究對象。
通過對各種智能化編程系統(tǒng)的調(diào)研分析,以推薦系統(tǒng)為例,根據(jù)推薦結(jié)果進(jìn)行分類,比較常見的推薦系統(tǒng)類型有方法塊推薦[1]、API 序列推薦[2]、token 以及tokens 推薦[4-5]等??偟膩碚f,其數(shù)據(jù)粒度小于等于方法塊,因此以方法塊作為數(shù)據(jù)質(zhì)量評估的基本單元具有代表性和通用性。因此,本文評估的對象選擇的是從開源項(xiàng)目中抽取的方法塊。
本文分別以線上和線下兩大類數(shù)據(jù)信息對源碼數(shù)據(jù)質(zhì)量進(jìn)行評估。
線上數(shù)據(jù)信息來自于GitHub 中包含的對應(yīng)項(xiàng)目信息。GitHub 代碼庫中包含對應(yīng)項(xiàng)目的各種統(tǒng)計信息,包括Watch、Star 和Fork 等,這些統(tǒng)計信息中隱含著對應(yīng)項(xiàng)目一定程度的質(zhì)量信息,如果能夠找到合適的指標(biāo)并充分使用,就能在一定程度上對項(xiàng)目質(zhì)量進(jìn)行評估。本文在充分理解各個統(tǒng)計指標(biāo)的基礎(chǔ)上,綜合使用各種指標(biāo)信息來對項(xiàng)目質(zhì)量進(jìn)行科學(xué)可信的評估。圖1 所示是GitHub 上單個項(xiàng)目的主頁中10個可能包含項(xiàng)目質(zhì)量信息的統(tǒng)計指標(biāo)。
線下數(shù)據(jù)信息來源于項(xiàng)目本身,主要是源碼質(zhì)量[6-7]信息、方法塊功能重復(fù)[8]信息和自定義方法調(diào)用信息等。因?yàn)楸疚倪x擇以方法塊作為數(shù)據(jù)質(zhì)量評估基本單元,所以除了源碼本身質(zhì)量以外,是否具有獨(dú)立、完整的功能也應(yīng)該作為方法塊數(shù)據(jù)質(zhì)量的衡量維度之一。
這些方法塊通常會被用于構(gòu)建智能化編程系統(tǒng)所使用的數(shù)據(jù)集,因此本文希望能夠幫助相關(guān)領(lǐng)域研究人員得到海量的、編程風(fēng)格良好的、具有盡可能少的缺陷以及具有獨(dú)立完整功能的方法塊數(shù)據(jù)集。
代碼數(shù)據(jù)質(zhì)量評估核心在于選用哪些維度進(jìn)行數(shù)據(jù)質(zhì)量衡量,以及如何具體地評估各個維度,方法則主要有定性和定量兩類。這也是本文主要的研究內(nèi)容。
本章研究回答兩個重要問題中的第一個,即開源項(xiàng)目托管平臺上的源碼數(shù)據(jù)可能存在哪些質(zhì)量問題。
本文的數(shù)據(jù)質(zhì)量評估方法不局限于具體的程序設(shè)計語言,為了方便描述,本文用Java 程序設(shè)計語言為例進(jìn)行陳述。
傳統(tǒng)衡量GitHub 代碼質(zhì)量的方法通?;陧?xiàng)目的star數(shù),即一個項(xiàng)目具有的star數(shù)越高,該項(xiàng)目質(zhì)量越高。某些公司在招聘開發(fā)人員時,一個重要的加分項(xiàng)就是應(yīng)聘者擁有高star數(shù)的GitHub 項(xiàng)目。然而,調(diào)查發(fā)現(xiàn),部分被調(diào)查者有過幫助GitHub 項(xiàng)目作者“刷star”的行為。正是這樣的欺詐行為的存在,使得GitHub 上低質(zhì)量的項(xiàng)目也可能具有較高的star 數(shù),因此本文將作者刷star 數(shù)量的行為作為一個重要的數(shù)據(jù)質(zhì)量參數(shù)。
本文希望能夠幫助智能化編程領(lǐng)域相關(guān)的研究人員得到海量的高質(zhì)量方法塊,因此如果能夠判定某個具有高質(zhì)量項(xiàng)目的作者確實(shí)是可信的,通常認(rèn)為該作者具有較高的編程能力。進(jìn)一步認(rèn)為該作者的相關(guān)項(xiàng)目具有較高的質(zhì)量,即使它們或許在單個項(xiàng)目統(tǒng)計指標(biāo)上的數(shù)據(jù)質(zhì)量并不是最優(yōu)。
GitHub 作為全世界最大的開源項(xiàng)目托管平臺,擁有海量的開源代碼項(xiàng)目,給源代碼方面相關(guān)研究提供了極為豐富的數(shù)據(jù)資源。但因?yàn)槠渥鳛轫?xiàng)目托管平臺,任何開發(fā)人員都可以在GitHub 上托管自己的任何項(xiàng)目。項(xiàng)目托管者可能是Apache、Google 這樣的正規(guī)組織及軟件公司,也有可能是正在學(xué)習(xí)編程開發(fā)的新手開發(fā)者。因此,開源平臺上的項(xiàng)目質(zhì)量也參差不齊,并不能保證都具有較高質(zhì)量。
項(xiàng)目本身作為比方法塊更大的粒度級別[9],其質(zhì)量的高低在一定程度上可以表征對應(yīng)方法塊的質(zhì)量。因此對方法塊進(jìn)行質(zhì)量評估,首先要對對應(yīng)的項(xiàng)目整體進(jìn)行評估。因此如何對海量的開源項(xiàng)目中單個項(xiàng)目進(jìn)行質(zhì)量評估也是一個重要的研究問題。
一個通過編譯的Java 項(xiàng)目,其源碼中仍然可能含有一些問題[10-12]。比如,不符合命名規(guī)則的變量或方法命名、未使用的局部變量或參數(shù)、空的try 語句等。如圖2 所示,一個能夠運(yùn)行的方法塊中仍然存在一些問題,1 和3 是不規(guī)范的變量命名,2 是沒有使用的對象。
從方法粒度級別來看,這些問題通常不會影響方法塊的功能實(shí)現(xiàn)。但在更小粒度上,比如進(jìn)行API、API 序列、token sequence 等相關(guān)研究時,上述問題就會產(chǎn)生較大影響。比如,進(jìn)行token sequence 相關(guān)研究時,需要對源碼中用戶自定義的變量名進(jìn)行統(tǒng)一化處理,而不符合命名規(guī)范的變量名可能會對該處理操作帶來困難。
因此,源碼本身也是代碼數(shù)據(jù)質(zhì)量評估的一個重要方面。源碼本身可能存在哪些問題和如何找出以及統(tǒng)計這些問題是本文一個重要的研究內(nèi)容。
刪除數(shù)據(jù)集中的重復(fù)方法塊可以解決數(shù)據(jù)冗余問題,盡可能使數(shù)據(jù)集具有最小性,在整個數(shù)據(jù)集層面上是必要的。但換個角度看,一個方法塊在整個數(shù)據(jù)集中的冗余程度越高,它所具有的功能就越常用[13]。比如,在Java 開發(fā)中,兩個方法塊分別具有功能“Write content to file”和功能“Serialize an object to a file”,兩個都是比較常見的功能需求。但是前一個功能更常見,所以一個進(jìn)行方法塊推薦的系統(tǒng)所使用的數(shù)據(jù)集中更應(yīng)該包含前者,否則可能會導(dǎo)致用戶需要卻無法獲取該功能。因此從方法塊數(shù)據(jù)質(zhì)量評估的角度來看,功能越重復(fù)的方法塊,它的質(zhì)量應(yīng)該越高。
因此在方法塊功能維度上,本文需要解決如何對方法塊相似度進(jìn)行計算[14]以及得到一個相似度閾值,使得能夠判定相似度大于該閾值的兩個方法塊功能是相似的。
正如之前所述,進(jìn)行質(zhì)量評估之后的方法塊會被用于構(gòu)建智能化學(xué)習(xí)的數(shù)據(jù)集,比如用于方法塊和API 序列等推薦。無論方法塊最終會被用于哪種類型的代碼推薦,它都應(yīng)該盡量具有獨(dú)立完整的功能,即在方法體中盡可能沒有對其他自定義方法的調(diào)用操作。
以方法塊推薦為例,如果一個方法塊中存在對其他自定義方法的調(diào)用,那么即使在最終推薦時用戶獲取到該方法塊,但由于調(diào)用方法的缺失,用戶也無法使用,這樣就使得推薦結(jié)果在一定程度上喪失了實(shí)用性。因此,如果一個方法塊中存在對自定義方法調(diào)用,該維度上應(yīng)該被評估具有較低的質(zhì)量。
本章研究回答之前所述兩個重要問題中的第2個,即如何利用定性或定量的方式對開源代碼數(shù)據(jù)質(zhì)量進(jìn)行評估。如圖3 所示,本文的評估方法包含5個維度。
Fig.2 Example of method that is still problematic through compiling圖2 一個通過編譯仍存在問題的方法塊示例
Fig.3 5 quality evaluation dimensions for open source big data圖3 面向開源源碼大數(shù)據(jù)的5個質(zhì)量評估維度
本文的評估方法充分利用作者可信度、項(xiàng)目健康度、源碼質(zhì)量、方法塊功能常用性和方法塊功能原子性5個維度信息,得到單個方法塊的評估結(jié)果。一個完整的評估流程如圖4 所示。
GitHub 的項(xiàng)目托管者刷star 數(shù)一般有兩種常見的方式:請其他的GitHub 用戶幫其進(jìn)行該行為和委托該服務(wù)的提供商實(shí)施該行為。一般來說,第一種規(guī)模較??;第二種,結(jié)合圖2 內(nèi)容可知,規(guī)??梢暂^大,并且可能存在同時刷star以及fork 的行為。
針對上述兩種情況,本文提出的解決方案是,通過從可信的GitHub 作者信息中獲取可信作者具有的一般規(guī)律。因此,本文的解決方法是通過在具有較高質(zhì)量的項(xiàng)目地址集上計算watch/(watch+star+fork)的值,評估項(xiàng)目作者可信度。具體來說,利用收集的365個具有較高質(zhì)量的項(xiàng)目地址,獲取其項(xiàng)目托管者主頁地址,進(jìn)而獲取該作者在GitHub 上所有項(xiàng)目地址。然后,利用獲取到的地址,獲取對應(yīng)項(xiàng)目watch、star 和fork 數(shù),將各項(xiàng)對應(yīng)相加之后,得到每個作者GitHub 所有項(xiàng)目得到的watch、star 和fork 總數(shù)。然后按照上述計算方法,得到watch/(watch+star+fork)的值,該值表征了該可信任GitHub 作者在該質(zhì)量維度上的定量情況。計算對應(yīng)作者所有項(xiàng)目總和在watch/(watch+star+fork)的值實(shí)際在一定程度上反映了該作者是否存在刷star 以及fork 的行為,比值越小,可能性越高。部分GitHub 作者對應(yīng)總watch、star和fork 數(shù)統(tǒng)計和比值情況如表1 所示。
Table 1 Numbers and ratios information of some GitHub authors’total watch,star and fork表1 部分GitHub 作者總watch、star和fork 數(shù)統(tǒng)計以及比值情況
為了避免極端數(shù)值的影響,閾值計算方式是將365個watch/(watch+star+fork)比值去掉5個最大值和5個最小值之后,計算剩余355個值的平均值作為最終的閾值。最終計算得到的閾值保留3 位小數(shù)后為0.058。因此,對GitHub 項(xiàng)目作者可信度的評估方法為,計算對應(yīng)作者所有項(xiàng)目總和在watch/(watch+star+fork)的值,如果值高于閾值0.058,則評估為可信。
Fig.4 Complete flow chart of data quality evaluation for method block圖4 一個完整的方法塊數(shù)據(jù)質(zhì)量評估流程圖
GitHub 每個項(xiàng)目主頁會顯示對應(yīng)項(xiàng)目的各種統(tǒng)計信息,包括Watch、Star 和Projects 等。為了進(jìn)行項(xiàng)目健康度評估,本文構(gòu)建了一個Java 項(xiàng)目數(shù)據(jù)集,共包含6 000個Java 項(xiàng)目地址,該數(shù)據(jù)集可以在一定程度上代表GitHub 總體Java 數(shù)據(jù)質(zhì)量情況。根據(jù)已有的數(shù)據(jù)集和指標(biāo),本文對項(xiàng)目質(zhì)量進(jìn)行評估的基本想法是,給出GitHub 總體Java 項(xiàng)目的一般性質(zhì)量表征,然后對單個Java 項(xiàng)目,根據(jù)其對應(yīng)指標(biāo)上的對比,可以得到該項(xiàng)目的一個定性的質(zhì)量度量。
在指標(biāo)選取上,根據(jù)對有GitHub 使用經(jīng)驗(yàn)的人員進(jìn)行廣泛的信息收集,最終確定選用的指標(biāo)為Watch、Star、Fork、Issues、Pull requests 和commits,并且對這6個指標(biāo)分別計算閾值,然后得到一個項(xiàng)目健康度的定性評估方法。
為了降低極端值對閾值的影響,本文先統(tǒng)計6 000個項(xiàng)目各個指標(biāo)值的對應(yīng)各個值出現(xiàn)次數(shù),按照出現(xiàn)次數(shù)從高到低進(jìn)行排序,然后取前0.3 的次數(shù)值計算平均值得到各個指標(biāo)對應(yīng)的閾值。閾值計算過程如算法1 所示。
算法1 項(xiàng)目健康度評估的閾值計算
如算法1 描述,首先對6 000個項(xiàng)目數(shù)據(jù),針對指標(biāo)Watch、Star、Fork、Issues、Pull requests 和commits分別獲取每個項(xiàng)目的單個指標(biāo)值,并統(tǒng)計各個指標(biāo)值的對應(yīng)各個值出現(xiàn)次數(shù)。比如,項(xiàng)目1 的Watch 指標(biāo)值為200,則以200 為Watch 指標(biāo)HashMap 的key、1為value,如果項(xiàng)目2 的Watch指標(biāo)值也為200,則HashMap 中key 為200 的value 變?yōu)?。循環(huán)執(zhí)行得到所有指標(biāo)對應(yīng)數(shù)值以及值的出現(xiàn)次數(shù)。然后,對各個指標(biāo)對應(yīng)的HashMap 按照value 大小從大到小排序,取前面的30%的數(shù)據(jù),取出HashMap 中key 和value值,并計算均值,即得到對應(yīng)指標(biāo)的閾值。
本算法的優(yōu)點(diǎn)在于:第一可以消除極端值對閾值的影響;第二可以利用更具有代表性的值來計算閾值。最終,保留3 位小數(shù)后,計算得到的各個指標(biāo)對應(yīng)閾值如表2 所示。
Table 2 Corresponding threshold value for each metric表2 各個指標(biāo)對應(yīng)閾值
因此,最終確定的對GitHub 項(xiàng)目質(zhì)量進(jìn)行評估方法為,采用定性的方式,待評估項(xiàng)目在對應(yīng)指標(biāo)上高于閾值則可以判定為質(zhì)量較高。此外,由于本文給出了每個指標(biāo)的對應(yīng)閾值,用戶也可以根據(jù)自身需求,只采用其中部分指標(biāo),或者是根據(jù)需要給指標(biāo)指定優(yōu)先級,進(jìn)而進(jìn)行項(xiàng)目質(zhì)量的評估。這樣可以更好地滿足用戶的特定需求,具有更好的實(shí)用性。
源碼質(zhì)量評估主要分析源碼本身可能存在哪些問題以及如何對這些問題進(jìn)行定性或定量度量。本文利用靜態(tài)代碼分析方法[15],使用PMD(programming mistake detector)來對源碼中缺陷進(jìn)行分析和統(tǒng)計。選擇PMD 的理由有兩點(diǎn):首先,PMD 是一種比較常用的靜態(tài)代碼分析工具,其性能值得信賴;此外,PMD 和腳本語言的結(jié)合使用,能夠?qū)ava 項(xiàng)目進(jìn)行批量化靜態(tài)分析。PMD 通過其內(nèi)置的編碼規(guī)則對Java 代碼進(jìn)行靜態(tài)檢查,主要包括對潛在的bug、未使用的代碼、重復(fù)的代碼、循環(huán)體創(chuàng)建新對象等問題的檢查,這些規(guī)則在一定程度上覆蓋了源碼本身可能存在的問題,因此可以充分利用已有規(guī)則找出源碼中可能含有的問題。
本文需要解決的一個問題是:PMD 進(jìn)行靜態(tài)代碼分析的基本單位是Java 文件,而本文的目標(biāo)是對一個Java 方法塊進(jìn)行缺陷類型和數(shù)量進(jìn)行統(tǒng)計。為了解決這個問題,可以將PMD 和Java 抽象語法樹(abstract syntax tree,AST)結(jié)合使用。
另一個問題是,Java 代碼中不同的問題對源碼數(shù)據(jù)質(zhì)量影響程度不同,因此對應(yīng)的PMD 內(nèi)置規(guī)則也應(yīng)該具有不同的優(yōu)先級。為了解決這個問題,將調(diào)查研究和統(tǒng)計方法相結(jié)合。首先,根據(jù)30個具有4~6年Java 開發(fā)經(jīng)驗(yàn)人員的意見,選擇比較重要的8個PMD 規(guī)則集。然后,在質(zhì)量比較高的Java 項(xiàng)目集中對不同PMD 規(guī)則集檢查出的問題進(jìn)行數(shù)量統(tǒng)計,在這些項(xiàng)目中某類問題出現(xiàn)次數(shù)越多,說明該類問題對源碼數(shù)據(jù)質(zhì)量影響越小。這里所使用的高質(zhì)量Java 項(xiàng)目集是具有較高質(zhì)量的項(xiàng)目中的Java 項(xiàng)目,共選用了45個。如表3 所示,是在45個高質(zhì)量Java 項(xiàng)目上統(tǒng)計出的8個PMD 規(guī)則集對應(yīng)的問題數(shù)量。
Table 3 8 types of PMD rules in high quality Java project sets表3 高質(zhì)量Java 項(xiàng)目集中8 類PMD 規(guī)則檢查情況
根據(jù)表3 的數(shù)量統(tǒng)計情況,可以得到各個規(guī)則集對應(yīng)的優(yōu)先級。在源碼質(zhì)量維度,本文使用這些PMD 規(guī)則集來進(jìn)行質(zhì)量評估,最終用戶可以根據(jù)各個規(guī)則集在某個方法塊中檢查出問題的數(shù)量,結(jié)合已經(jīng)測定的優(yōu)先級,對該方法塊質(zhì)量進(jìn)行定性的評估。
一個方法塊在整個數(shù)據(jù)集中冗余程度越高,對該方法塊自身而言,它所具有的功能就越常用。因此,本文從方法塊功能常用性維度對其質(zhì)量進(jìn)行評估。在該維度上,需要確定方法塊相似度的計算方法以及相似度閾值的計算方法。
本文選擇使用Simhash[16-17]方法計算方法塊相似度。選擇的原因主要有兩個:(1)Simhash 是用來進(jìn)行網(wǎng)頁去重常用的高效方法,而評估方法塊功能是否常見需要將單個方法塊和數(shù)據(jù)集中每個方法進(jìn)行相似度計算,因此計算速度對實(shí)用性影響較大;(2)Simhash 是一種局部敏感hash,如果兩個字符串具有一定的相似性,在hash 之后,仍然能保持這種相似性。而這是進(jìn)行代碼相似度計算中的重要特性。
在相似度閾值計算方面,首先從Stack Overflow和相關(guān)論文中獲取10個比較常見的Java 方法塊功能需求。然后,將10個指定的功能發(fā)布給30個具有4~6年Java 開發(fā)經(jīng)驗(yàn)的開發(fā)人員進(jìn)行Java 方法塊編寫,最終得到10 組共300個具有相同功能的方法塊。相似度閾值通過對10 組方法塊計算相似度并取平均得到,保留兩位小數(shù)之后的值為0.82。
本文考慮對單個方法塊質(zhì)量進(jìn)行評估,而不是構(gòu)建方法塊數(shù)據(jù)集,因此還需構(gòu)建一個用于和被評估方法塊計算相似度的方法塊數(shù)據(jù)集。并且,將不具有實(shí)際功能的main()函數(shù)、set()/get()函數(shù)、測試單元以及部分重寫函數(shù)等函數(shù)進(jìn)行清除。最終可以根據(jù)給定的數(shù)據(jù)集,計算待評估方法塊與數(shù)據(jù)集中方法塊功能的相似性,并根據(jù)閾值評估該方法塊功能的常見程度,用戶可以決定是否使用該方法塊。
方法塊功能的獨(dú)立完整性作為方法塊數(shù)據(jù)質(zhì)量評估的一個維度是有必要的。這里需要統(tǒng)計方法塊中對自定義方法的具體的調(diào)用次數(shù)。
首先,對一個Java 項(xiàng)目中所有Java 文件分別構(gòu)建一個抽象語法樹。利用該語法樹來識別Java 類中所有方法調(diào)用以及其所屬的方法塊。對方法中的所有方法調(diào)用進(jìn)行處理之后,可以得到對應(yīng)方法塊中所有方法調(diào)用所使用方法的方法名及所屬類,然后以類名+方法名的形式進(jìn)行保存。對方法塊進(jìn)行識別、切分和保存之后,可以進(jìn)一步抽取所有方法塊對應(yīng)方法名及其所屬的自定義Java 類,進(jìn)而得到單個Java 項(xiàng)目中所有的自定義方法的方法名,并同樣以類名+方法名的形式進(jìn)行保存。最后,將單個方法所調(diào)用方法和自定義方法進(jìn)行比較,如果存在交集,則存在自定義方法調(diào)用情況,也可以統(tǒng)計出總的調(diào)用次數(shù)。并且,由于利用了方法所屬類的信息,即使存在自定義方法和Java 已有方法或第三方JAR 包中方法同名的現(xiàn)象,也能根據(jù)所屬類信息進(jìn)行區(qū)分。而類名和方法名都重名的情況,本文認(rèn)為該情況比較極端,暫且不予考慮。
因此針對方法塊功能完整性評估,最終得到的是單個方法塊中對自定義方法的調(diào)用次數(shù)。根據(jù)該值,用戶可以判斷對應(yīng)方法塊功能是否獨(dú)立完整,以及對其他方法塊功能依賴程度,最終決定是否使用該方法塊。
本章系統(tǒng)化介紹對GitHub 上一個Java 項(xiàng)目實(shí)施完整的數(shù)據(jù)質(zhì)量評估過程,將結(jié)合具體實(shí)例對提出的方法塊評估方法的有效性進(jìn)行驗(yàn)證。主要針對包含數(shù)值計算和閾值的維度進(jìn)行驗(yàn)證,即項(xiàng)目作者可信度、項(xiàng)目健康度和方法塊功能常用性維度。而源碼質(zhì)量和方法塊功能完整性維度是指導(dǎo)性的評估,用戶根據(jù)自身需求決定是否使用,本文不再專門進(jìn)行有效性驗(yàn)證。
本章在開源軟件項(xiàng)目托管平臺GitHub 上收集開源項(xiàng)目數(shù)據(jù)用于進(jìn)行數(shù)據(jù)質(zhì)量問題分析,按照需求的不同收集了兩種不同質(zhì)量級別的項(xiàng)目地址集。
第一種是具有平均數(shù)據(jù)質(zhì)量的項(xiàng)目集地址,本文將該數(shù)據(jù)集作為GitHub 總體項(xiàng)目數(shù)據(jù)子集,能夠在一定程度上代表GitHub 總的數(shù)據(jù)質(zhì)量情況。因此,本文的收集方法是通過language 和star 對項(xiàng)目數(shù)據(jù)地址進(jìn)行檢索爬取。為了更具一般性,取star 數(shù)在0~10 000 之間,以這樣的方式爬取到6 000個Java 項(xiàng)目地址,具有典型性和代表性。
第二種是具有較高質(zhì)量的項(xiàng)目集地址,進(jìn)而獲取其項(xiàng)目托管者主頁地址,這里不再針對特定語言。本文收集了365個,語言包括C、C++、Java、C#、Android、iOS 以及Python 在內(nèi)的,公認(rèn)具有較高質(zhì)量的項(xiàng)目的作者主頁地址,具有典型性和代表性。考慮到本文是利用高質(zhì)量項(xiàng)目對應(yīng)作者的信息來計算項(xiàng)目作者可信度閾值,相當(dāng)于使用了365個專家信息,可以滿足閾值的計算需求。部分項(xiàng)目信息如表4所示。
Table 4 Information of partial project examples with high quality表4 部分所使用的高質(zhì)量項(xiàng)目信息示例
為了更好地理解本文評估方法的評估過程,本文從GitHub 中隨機(jī)抽取一個Java 項(xiàng)目進(jìn)行實(shí)例應(yīng)用分析,項(xiàng)目主頁鏈接為https://github.com/mi***cs/mi***er。
首先進(jìn)行項(xiàng)目作者可信度評估。利用項(xiàng)目主頁鏈接,可以獲取到對應(yīng)作者主頁鏈接為https://github.com/mi***cs,進(jìn)而統(tǒng)計該作者對應(yīng)的所有項(xiàng)目的watch、star 和fork 數(shù)量,分別為157、1 679 和292,計算watch/(watch+star+fork)比值為0.074。該值大于項(xiàng)目作者可信度閾值0.058,因此在項(xiàng)目作者可信度維度可以判定該項(xiàng)目的作者是可信的。
進(jìn)行項(xiàng)目健康度評估時,根據(jù)項(xiàng)目主頁鏈接可以獲取到Watch、Star、Fork、Issues、Pull requests 和commits 這6個指標(biāo)值分別為121、1 338、275、97、25和1 366,分別大于對應(yīng)閾值11、76、28、4、1 和58。因此,在項(xiàng)目健康度維度該項(xiàng)目評估為健康。
在源碼質(zhì)量評估中,利用AST 和PMD 將項(xiàng)目中所有Java 文件以方法塊為單位進(jìn)行切分,并得到每個方法塊中不同PMD 規(guī)則檢測出的缺陷數(shù)量。該項(xiàng)目切分得到的方法塊數(shù)量為380,每個方法塊中對應(yīng)各個規(guī)則缺陷數(shù)量不等。以方法塊metricData 為例,該方法塊中有3個rulesets/Java/naming 規(guī)則檢測出的規(guī)范,而該規(guī)范優(yōu)先級較低,即在一定程度上是可以接受的。因此,該源碼質(zhì)量評估中,方法塊metricData可以評估為具有較高質(zhì)量。
進(jìn)行方法塊功能常用性評估時,同樣以方法塊metricData 為例,先計算該方法塊和方法塊數(shù)據(jù)集中每個方法塊相似度,計算后得到相似度最大為0.78,小于閾值0.82。因此,在方法塊功能常見性維度,該方法塊功能不是較常見的功能。
在方法塊功能原子性評估中,利用AST 得到該方法塊中調(diào)用的方法數(shù)量為6,但都不是自定義方法,也就是說該方法對自定義方法調(diào)用為0。因此,該方法塊功能具有原子性。
綜合上述5個維度的評估結(jié)果,雖然該方法塊功能不是較常見的功能,但在其他4個維度的評估中評價較高,因此最終評估該方法塊具有較高的質(zhì)量。
同理,該項(xiàng)目對應(yīng)的其他379個方法塊按照metricData 的評估方式,可以繼續(xù)得到源碼質(zhì)量評估、方法塊功能常用性評估和方法塊功能原子性評估的評估結(jié)果,得到5個不同維度的最終評估結(jié)果。最終,該項(xiàng)目對應(yīng)的380個方法塊中,337個方法塊評估為具有較高質(zhì)量,其他的43個方法塊質(zhì)量評估為較低。
對于作者可信度的評估方法是計算對應(yīng)作者所有項(xiàng)目總和在watch/(watch+star+fork)的值,值高于閾值0.058 評估為可信。為了驗(yàn)證該方法和該閾值是否有效,本文隨機(jī)爬取GitHub 中10個watch/(watch+star+fork)的值低于該閾值的項(xiàng)目作者主頁,然后人為分析對應(yīng)作者所有項(xiàng)目中是否存在有問題的項(xiàng)目。如表5 所示,是10個評估方法判定為不可信作者的具體信息統(tǒng)計情況。
Table 5 Statistics on 10 untrusted authors through proposed evaluation approach表5 10個評估為不可信作者的信息統(tǒng)計
從表5 可以看出,大部分項(xiàng)目作者可信度維度評估為不可信的作者最終人為檢查中也是有問題的。這能夠說明,至少在項(xiàng)目作者可信度這個維度上,本文的評估方式是比較合理的。
一個需要解釋的地方是,10個評估為不可信的項(xiàng)目作者中有4個被人為判定為是可信的,這是因?yàn)楸疚膶?xiàng)目作者可信的評估比較嚴(yán)格。因?yàn)楸疚南M軌蛲ㄟ^該維度的評估來幫助相關(guān)的研究人員得到海量的高質(zhì)量方法塊,所以判定某個具有高質(zhì)量項(xiàng)目的作者確實(shí)是真實(shí)可信的,就認(rèn)為該作者確實(shí)具有較高的編程能力。進(jìn)一步就可以將該作者所有項(xiàng)目都視為具有較高的質(zhì)量。因此總的來說,本文對項(xiàng)目作者可信度的評估方法以及評估閾值的設(shè)定還是比較合適的,確實(shí)能夠在一定程度上識別有問題的項(xiàng)目作者。
對GitHub 項(xiàng)目健康度進(jìn)行評估方法為,在對應(yīng)指標(biāo)Watch、Star、Fork、Issues、Pull requests 和commits上高于測定閾值則可以判定為質(zhì)量較高。因此,為了對該評估方法進(jìn)行驗(yàn)證,本文隨機(jī)爬取了5個在不同指標(biāo)上低于對應(yīng)閾值的項(xiàng)目,然后人為分析其對應(yīng)項(xiàng)目源碼,判定其質(zhì)量高低。具體項(xiàng)目信息統(tǒng)計情況如表6 所示。
Table 6 Statistics on 5 low-quality projects through proposed evaluation approach表6 5個評估為低質(zhì)量項(xiàng)目的信息統(tǒng)計
通過表6 的內(nèi)容,可以發(fā)現(xiàn),5個在項(xiàng)目健康度維度評估為質(zhì)量較低的項(xiàng)目,在人為評估中確實(shí)是由于各種不同的原因而具有較低的質(zhì)量。并且其對應(yīng)各個評估指標(biāo)都具有較差的表現(xiàn)。
和項(xiàng)目作者評估類似,本文對項(xiàng)目健康度的評估也比較嚴(yán)格。因?yàn)楸疚牡拿嫦驅(qū)ο笫侵悄芑幊滔到y(tǒng),比如代碼推薦系統(tǒng),源碼質(zhì)量可能對整個系統(tǒng)的性能影響都很大,本文希望能夠盡可能地只收集質(zhì)量較高的項(xiàng)目。因此,可能會舍棄掉一些質(zhì)量并不低的項(xiàng)目。
本文對項(xiàng)目健康度的評估方法以及評估閾值的設(shè)定還是比較合適的,能夠在一定程度上篩選出質(zhì)量較高的項(xiàng)目。
針對方法塊功能常用性的評估是根據(jù)本文構(gòu)造的數(shù)據(jù)集,計算待評估方法塊與數(shù)據(jù)集中方法塊功能的相似性,然后可以根據(jù)閾值評估該方法塊功能的常見程度。因此,對方法塊功能常用性維度進(jìn)行驗(yàn)證的方法是,對數(shù)據(jù)集中方法塊相似度大于閾值的方法塊功能進(jìn)行人為獲取,進(jìn)而判斷對應(yīng)功能是否常見。具體來說,直接計算數(shù)據(jù)集中方法塊之間相似度,并將相似度大于閾值的方法塊歸為一簇。對簇規(guī)模較大的簇中方法塊功能常用性進(jìn)行評估。為了和已構(gòu)建的方法塊數(shù)據(jù)集進(jìn)行區(qū)分,從GitHub上另外爬取了200個Java 項(xiàng)目來構(gòu)建驗(yàn)證所使用數(shù)據(jù)集,切分得到方法塊總數(shù)為118 254。表7 所示為10個較大簇方法塊功能信息。
Table 7 Statistics on commonly-used function information in 10 clusters表7 10個方法塊簇功能常用性信息
通過表7 的內(nèi)容可以發(fā)現(xiàn),統(tǒng)計的10個規(guī)模較大的簇中方法塊都具有較為清晰的功能實(shí)現(xiàn),并且從功能上看也是比較常見的一些Java 功能需求。從每個簇中方法塊數(shù)量來看,雖然數(shù)量大小和對應(yīng)功能的常用性并不是嚴(yán)格一致,但是總體來說仍然具有一定的正相關(guān)性。
根據(jù)驗(yàn)證結(jié)果,本文給出的方法和測定的閾值確實(shí)能在一定程度上篩選出功能比較常見的方法塊。因此,本文認(rèn)為對方法塊功能常用性評估方法是比較合適的。
本文通過大量調(diào)研發(fā)現(xiàn),源碼數(shù)據(jù)的質(zhì)量對源碼相關(guān)的研究有重大影響,并最終會對推薦結(jié)果的質(zhì)量產(chǎn)生影響。這一點(diǎn)本文之前的代碼推薦相關(guān)的研究工作中已經(jīng)得到證實(shí)。
而已有的一些對收集到的數(shù)據(jù)進(jìn)行處理的工作相對簡單。比如,江賀等人在進(jìn)行方法塊推薦的相關(guān)研究時,對采集的數(shù)據(jù)進(jìn)行了簡單的篩選處理,這難以滿足研究人員對代碼數(shù)據(jù)質(zhì)量的要求。已有的聚焦于源碼數(shù)據(jù)質(zhì)量的研究工作較少,并且更關(guān)注如何對數(shù)據(jù)進(jìn)行清洗問題,如周傲英等人的研究重點(diǎn)就是對數(shù)據(jù)進(jìn)行清洗。他們較為具體地說明了數(shù)據(jù)質(zhì)量的重要性和衡量指標(biāo),定義了數(shù)據(jù)清洗問題。然后對數(shù)據(jù)清洗問題進(jìn)行分類,并分析了解決這些問題的途徑。還說明數(shù)據(jù)清洗研究與其他技術(shù)的結(jié)合情況,并分析了幾種數(shù)據(jù)清洗框架。
而在本文中,綜合考慮了項(xiàng)目作者可信度、項(xiàng)目健康度、源碼質(zhì)量、代碼塊功能常用性和代碼塊功能原子性,共5個維度對代碼塊質(zhì)量進(jìn)行評估,而不是對源碼數(shù)據(jù)進(jìn)行篩選或者清洗。本文最終給出對單個代碼塊的質(zhì)量評估結(jié)果,將代碼塊的篩選工作交由進(jìn)行具體研究工作的研究人員來完成,研究人員可以根據(jù)自身需求進(jìn)行自主選擇是否使用某個代碼塊。
本文方法的有效性在5.3 節(jié)進(jìn)行了驗(yàn)證。對于作者可信度評估方法的驗(yàn)證,結(jié)果如5.3 節(jié)中表5 所示。從表5 可以看出,大部分項(xiàng)目作者可信度維度評估為不可信的作者最終人為檢查中也是有問題的。這能夠說明,在項(xiàng)目作者可信度這個維度上,本文的評估方式是比較合理的。對項(xiàng)目健康度評估方法的驗(yàn)證,結(jié)果如5.3 節(jié)表6 所示。5個被項(xiàng)目健康度評估維度的評估方法評估為質(zhì)量較低的項(xiàng)目,在人為評估中確實(shí)是由于各種不同的原因而具有較低的質(zhì)量。這在一定程度上說明了本文的項(xiàng)目健康度評估方法的有效性。針對方法塊功能常用性評估方法的有效性驗(yàn)證,結(jié)果如5.3 節(jié)表7 所示。可以發(fā)現(xiàn),本文給出的方法和測定的閾值確實(shí)能在一定程度上篩選出功能比較常見的方法塊。因此,本文認(rèn)為方法塊功能常用性評估方法是有效的。
綜上所述,數(shù)據(jù)質(zhì)量問題相當(dāng)重要但是沒有引起足夠重視,本文方法較為有效地彌補(bǔ)了編程智能化相關(guān)研究在數(shù)據(jù)質(zhì)量評估問題上的不足,具有一定的實(shí)用性和創(chuàng)新性。
首先會對本文的面向開源源碼大數(shù)據(jù)質(zhì)量評估方法的性能產(chǎn)生影響的是項(xiàng)目作者可信度維度。本文對該維度的評估主要是利用watch/(watch+star+fork)比值,因?yàn)楸疚目紤]刷star 數(shù)的兩種方式是請其他的GitHub 用戶幫助進(jìn)行該行為,以及委托專門提供該服務(wù)的服務(wù)商實(shí)施該行為,尤其是考慮到大量刷star 的行為只能通過服務(wù)商提供。因此,本文認(rèn)為所提出的針對該維度的評估方式是比較合適的。但是,如果一個項(xiàng)目刷star 的方式主要是請其他的GitHub 用戶幫助進(jìn)行該行為,并且他委托的用戶有很多,那么就可能造成對watch、star和fork的數(shù)量都有舞弊的行為,在這種情況下,本文針對該維度的評估方法可能就不太適用了。雖然這是一種極端情況,但是該情況確實(shí)對本文方法的有效性有很大的威脅。因此,這個問題會在未來工作中進(jìn)行進(jìn)一步研究。
此外,本文的評估方法當(dāng)前主要針對Java 語言。理論上本文的方法適用于所有編程語言。但是,由于本文只對Java 語言項(xiàng)目進(jìn)行了研究,而沒有考慮其他語言項(xiàng)目的特點(diǎn),因此編程語言可能也是一個對本文方法有效性產(chǎn)生威脅的一個比較重要的因素。將來,會結(jié)合不同編程語言各自的特點(diǎn),將本文的方法擴(kuò)展到其他的語言環(huán)境。
高質(zhì)量方法塊是進(jìn)行智能化編程及相關(guān)研究工作的基礎(chǔ)。隨著基于開源源碼的智能化軟件開發(fā)日益盛行,研究人員也逐漸認(rèn)識到源碼數(shù)據(jù)質(zhì)量的重要性,并嘗試進(jìn)行了一些簡單的數(shù)據(jù)處理。然而,當(dāng)前對于源碼數(shù)據(jù)質(zhì)量問題的關(guān)注度還比較缺乏。因此,本文面向相關(guān)研究中經(jīng)常使用的開源項(xiàng)目托管平臺上的代碼數(shù)據(jù),根據(jù)開源源碼中可能存在的數(shù)據(jù)質(zhì)量問題,從不同的維度,提出一種針對開源大數(shù)據(jù)的代碼數(shù)據(jù)質(zhì)量評估方法。本文旨在讓從事相關(guān)研究的開發(fā)人員能夠通過本文方法對研究中所使用的方法塊質(zhì)量進(jìn)行系統(tǒng)的評估,從而提高智能化軟件開發(fā)水平和質(zhì)量。
未來工作將繼續(xù)關(guān)注編程智能化方面的相關(guān)工作,包括將本文的數(shù)據(jù)質(zhì)量評估方法應(yīng)用到其他語言以及研究其他語言采用的代碼檢測工具及使用方法的工作。將深入進(jìn)行評估方面的研究。目標(biāo)是能夠?qū)崿F(xiàn)對智能化編程系統(tǒng)所使用數(shù)據(jù)集質(zhì)量的自動化評估、所使用測試集的自動構(gòu)建、所使用算法的自動分析和智能化編程系統(tǒng)評估使用的指標(biāo)的自動選取及可解釋性分析等。同時對常見的,如API 及方法塊推薦等,建立完整的自動化、智能化和可解釋性較好的評估系統(tǒng)。