APP下载

效力优化的代码评审者推荐模型

2018-11-14张小鹏赵逢禹

小型微型计算机系统 2018年11期
关键词:效力代码准确率

张小鹏,赵逢禹,刘 亚

(上海理工大学 光电信息与计算机工程学院,上海 200093)

1 引 言

在大型软件项目设计开发过程中,代码评审(Code Review)是发现代码缺陷进而提高软件质量的重要手段.Bavota等人[1]通过对三个开源系统的探索性研究,旨在调查代码评审对代码缺陷修复和提交代码组件质量的影响.他们的研究表明手动评审代码对软件项目的代码质量有着重大的影响.QT、Android和Open Stack软件项目为了维护项目的代码质量,更是保持了一个庞大的代码评审团队[2].由此可见代码评审确实能够更好的保障软件项目的质量.

目前关于代码评审的研究主要集中在代码评审时的责任分配[3,4]、对软件项目质量的影响[1,2,5]、评审方法研究[6]和自动的推荐代码评审者等方面.Weiss[7]等人研究发现,针对开源软件项目中的代码提交,具有评审者分配问题的代码提交时间相比没有分配问题的提交时间平均会多花费6到12天.更重要的是,有些提交的代码从未收到任何代码评审意见,也就无法被合并到主代码库.由此可以看出,如何为代码找到合适的评审者对保障软件系统的质量、提高软件的开发效率是非常有价值的.

在早期的代码评审推荐研究中,McDonald和Ackerman改进了基础的Line 10 Rule评审者推荐算法,使用了三种数据来标识评审者[8].该算法首先要求所有的评审者都要创建自己的概要文件;然后使用提交日志信息统计每个评审者评审过的模块总数;最后从问题跟踪器中为具有代表性的问题描述建立索引.利用这些数据,可以根据新提交问题的描述进行评审者的推荐.

Balachandran提出了基于修改历史的评审者推荐算法Review Bot[9].它利用代码层次的修改历史来推荐评审者.如果一次新提交所涉及的修改代码拥有修改历史,Review Bot将会为候选的评审者计算相应修改代码的修改次数.

Thongtanunam等人提出了利用文件路径相似性推荐代码评审者的FPS(File Path Similarity)算法[10].该算法假设大多数大型软件项目的目录结构是规范的和组织良好的,文件路径与其功能是密切相关的.算法利用候选评审者的历史评审文件路径和新提交代码涉及到的文件路径的相似性来推荐评审者.在其随后的研究[11]中进一步使用了更加复杂的路径相似性算法,比较两条路径的最长公共前缀、子序列等其他信息,并且添加了新的开源项目(Libre Office)来检验其效果.

Jiang等人利用开发者与评审者之间的社会关系属性来推荐代码评审者[12].他们研究发现使用机器学习中的Support Vector Machines方法可以得到最好的推荐表现.但是因为他们的算法使用的实验数据无法从其他软件项目的公开数据中获取,所以他们的研究结果没有重复性和可比性.

上述评审者推荐方法大都没有考虑到评审数据的时间效力和细粒度的评审内容.评审的时间性能够反映出评审者当前的评审重心,所以越是近期的评审越重要,在进行推荐时需要为当前的评审赋予更高的时间效力,让其发挥更大的作用.Thongtanunam等人使用了文件路径来区分源代码的功能,从而计算相似性,但这是一种粗粒度方法,无法详尽的反映评审者的具体评审内容,所以需要一种更细粒度化的标准来判别评审者的具体工作内容,这样就能够得到更准确的内容相似性.

针对以上问题,本文提出了效力优化的代码评审者推荐模型OCRRM(optimized code reviewer recommendation model).OCRRM模型首先根据评审的发生时间调整本次评审的时间效力,为最近的评审赋予更高的时间效力,然后将候选评审者的历史评审信息提取为细粒度的更具体的能够详细反映评审者具体评审内容的信息,将提交代码信息和候选评审者的历史评审详细信息的相似性作为内容效力,最后利用候选评审者的每次历史评审的时间效力作为内容效力的权重来综合推荐合适的代码评审者.效力优化主要是利用时间效力调整内容效力的权重,既能够利用详细的具体的评审内容,又能够让近期的历史评审发挥更大的作用,所以可以能够有效推荐合适的代码评审者.

2 效力优化的代码评审者推荐模型

评审者的历史评审数据主要分为两部分:评审者R的个人信息、评审者R的历史评审信息集合.R的历史评审数据可以表示为HRD(R)=.R.Profile表示评审者R的个人信息,包括R的唯一标识ID、姓名、邮箱、注册时间等.R.Reviews表示评审者R的历史评审信息集合,可以表示为:

R.Reviews = {}

其中Owneri、Datei、RCodei和Commentsi分别表示R的第i次历史评审的代码提交者、提交时间、评审的代码信息和评审流程中的所有评论.RCodei是通过分析修改的源代码得到的文件名、方法名的信息集合,可以表示为:

RCodei=

不同时期的历史评审活动对评审者的时间贡献效力是不同的,近期的评审数据更能够反映出评审者近期的评审重点.而且即使是同一个源代码文件,不同的评审者的评审内容和评审贡献也是不同的.因而本文利用历史评审数据的时间效力和内容效力对代码评审者推荐模型进行优化,利用时间效力和内容效力来联合推荐合适的代码评审者.图1给出了OCRRM的活动处理流程.

图1中的OCRRM模型主要包含六个步骤:

1)获取历史评审信息

为了内容效力的计算,需要首先获取所有的历史评审信息.利用网络爬虫从数据来源网站上获取历史评审的源数据,然后将源数据分析整理为统一的HRD(R)格式,得到格式化的历史评审数据集合,即HRD集合;

图1 OCRRM模型流程图

2)信息提取

利用文本提取从系统提交日志中提取出提交代码的提交者信息,然后使用AST技术对源代码中被修改的部分进一步分析,提取被修改代码涉及到的类、方法等详细内容;

3)获取候选评审者集合

如果某个文件被某个评审者评审过,那么当它被再次修改时,就应该寻找曾经评审过该文件的评审者作为候选评审者.如果新提交代码涉及到的文件都没有评审历史,那么全体评审者都是其候选评审者.如果涉及到的文件拥有评审历史,那么就应该在HRD集合中寻找曾经评审过该文件的评审者,并将该评审者加入候选评审者集合;

4)内容效力计算

内容效力CE度量候选评审者历史评审内容和新提交代码内容的相似度,内容越相似,内容效力越大.候选评审者的每次历史评审数据都会涉及到不同的源代码修改,使用AST技术将每次源代码中修改部分提取为更具体的内容,例如文件名、类名、方法名信息,可以反映出评审者的主要审核内容.然后利用改进的Jaccard相似度计算候选评审者的历史评审内容和提交代码内容的相似度,即内容效力得分;

5)时间效力计算

时间效力TE度量候选评审者某次历史评审发生时间和与当前时间的时间间隔,间隔越小,时间效力越大.若候选评审者R的某次评审发生于t天之前,则这次评审的时间效力为1/(t+1),t>=0;

6)综合推荐评审者

取得每个候选评审者的每次历史评审的时间效力和内容效力后,就可以综合两部分来推荐合适的评审者.为了防止越推荐越集中,越集中越推荐的情况,本文认为只有内容效力不为0的历史评审才是具有效力的历史评审,候选评审者的推荐得分是由所有具有效力的历史评审的时间效力和内容效力的乘积的和累加后除以有效评审次数得到的平均值,计算方法如公式(1)、公式(2)所示:

(1)

(2)

公式(1)、公式(2)中n表示候选的评审者R总的历史评审次数,CEi表示第i次历史评审的内容效力,TEi表示第i次历史评审的时间效力,C表示在n次历史评审中具有效力的评审次数,即CEi大于0的评审次数.这样求得的推荐平均值就能够剔除那些完全和新提交代码无关的评审的影响,也能够削弱评审者因为差异巨大的评审次数造成的影响.

计算出每个候选评审者的推荐得分后,根据推荐得分对候选评审者排序,然后就可以推荐前K名评审者.

3 评审者推荐关键技术

在OCRRM模型中关键的技术主要有获取历史评审信息、候选评审者集合的获取、历史评审的时间效力和内容效力的计算.

3.1 获取历史评审信息

本文选取了三个网站的评审数据进行分析,它们分别为QT、Android和Open Stack.这三个网站都可以获取JSON格式的评审数据,并且数据格式是相似的,这为数据的获取提供了极大的便利.以QT项目为例,一次完整的评审数据主要包括评审代码的提交信息、评审者、版本数、不同版本涉及到的源代码和评审者对不同版本代码的评论.利用网络爬虫从来源网站上获取存在于detailjson、detailServicejson和patchesjson中的源数据,通过解析json数据,从detailjson中获取评审涉及到的提交者、评审者、提交日志信息,从detailServicejson中获取所有的提交源文件、版本数、评审评论等信息,从patchesjson中获取某一版本涉及到的修改源文件、提交信息,最后将解析结果存入本地数据库.获取所有的解析数据后,将其再次处理格式化为HRD格式的数据存入数据库.这样所有的数据就获取处理完成,需要的时候只要访问本地数据库即可.

3.2 获取候选评审者

为了推荐合适的代码评审者,需要首先获取候选的代码评审者.如果一名提交者的提交代码中的某个文件被某名评审者多次评审,那么当提交者再次提交该段代码时,就应该找该名评审者来评审.

为了快速获取候选的评审者集合,算法使用提交代码信息NFiles、所有的历史评审数据HRD集合作为输入,输出候选评审者集合Revs.NFiles包含新提交代码中涉及到的所有文件名.程序遍历HRD集合,从中取出每一条HRD(R)数据,然后遍历HRD(R)数据中的R.Review集合.如果NFiles中的文件被R.Review评审过,即评审者某次评审的文件中包含新提交代码中的任一文件,那么就将该条HRD(R)所属的R.Profile加入输出的评审者集合Revs.

获取候选评审者伪算法如下:

输入:代码的提交者信息 NFiles=,所有的历史评审数据HRD集合输出:候选评审者集合 Revs1 //遍历HRD集合 2 For HRD(R)∈HRD3 //遍历HRD(R)的R.Review4 For R.Review∈HRD(R)5 //如果某次评审的文件包含新提交代码中的文件6 If R.Review.RData.Files∩NFiles!=null7 //R.Profile加入输出集合中8 Revs.add(R.Profile)9 End If10 End For11 End for12 返回Revs

3.3 时间效力计算

候选评审者的历史评审数据包含了评审者开始评审该项目到至今的所有评审数据,时间跨度可能很长.如果将所有时间跨度的评审数据的时间效力看作一样的,则会出现让一个长久没有评审的评审者评审新提交代码的情况.为了把代码推荐给能够及时反应的评审人员,需要使用效力优化函数对不同时间跨度的历史评审数据的时间效力进行调整.对于某位候选评审者R,第i次历史评审的时间效力计算如公式(3)如示:

(3)

公式(3)中DN(以天为时间度量单位)表示当前时间,DRCi代表R第i次历史评审的发生时间.评审者R的历史评审发生时间距当前时间越近,则t越小,时间效力越大,最大为1,最小趋近于0.为了防止除0,在分母上加1.

3.4 内容效力计算

某段代码可能会被修改和提交评审过多次,产生多个版本.本文将每次代码的修改提交都看作一次评审,即对于每一版本的代码修改都看作是一次评审,这样就可以充分利用足够细化的数据.但是通过对评审的评论分析发现,在评审的版本演进过程中,并不是所有的评审者都在评审过程中留下了评论,这就造成了某些评审者的评审意见为空.可是他们作为评审流程的一员,应该是做出了部分贡献,理应拥有评审数据,所以本文将版本演进造成的多次评审中的第一版评审数据作为所有评审者的基本数据.以QT项目的153840号Project评审*https://codereview.qt-project.org/#/c/153840/为例,该Project共有四个版本,看作四次评审,Patch Set 1中修改的类和方法作为该次评审所有评审者的基本数据.通过评论发现,Patch Set 2的评审数据应该是Leena的,而Patch Set 3和Patch Set 4号的评审数据分别是属于Marc和Olivier的.

在得到评审者的历史评审内容和新提交代码内容后,使用改进的Jaccard相似度计算方法可以计算出评审者每一次的评审代码内容和新提交代码内容的相似度,即每一次的评审内容效力.

Jaccard相似度[13]是用来度量两个不同维数集合之间的相似程度,又称之为狭义Jaccard相似度,两个集合的狭义相似度等于两个集合的交集比上两个集合的并集.但是本文在以新提交代码内容为基础度量新提交代码内容和历史评审内容的相似度时,更应该着重注意历史评审内容对新提交代码内容的覆盖程度,即提交代码内容和历史评审内容的共有元素个数越多,对新提交代码内容的覆盖程度越大,相似度越大.为此,本文提出了改进的Jaccard相似度,利用改进Jaccard相似度计算新提交代码内容和历史评审内容的相似性.设新提交代码的类集合P共有i个元素,历史评审数据的类集合R共有j个元素,则P和R的交集G共有k个元素,如公式(4)-公式(6)所示:

P={p0,p1,…,pi}

(4)

R={r0,r1,…,rj}

(5)

G=P∩R={g0,g1,…,gk}, 0≤k

≤Min(i,j)

(6)

以P和R为基础计算改进Jaccard相似度,如公式(7)所示:

(7)

公式(7)中|P|表示集合P的模,即P中元素的个数,|P∩R|表示集合P与R交集的模.k/i越大,表示评审内容和新提交代码内容的共有元素个数越大,即候选评审者评审内容和新提交代码内容越相近.

通过AST技术对评审者的历史评审源代码进行分析,提取其中被修改的类名和方法名.若评审者R的第i次历史评审的类名相似度为CJ,方法名相似度为MJ,则R的第i次历史评审内容的内容效力CE计算方法如公式(8)如表示:

CE(R,i)=a*CJ+(1-a)*MJ

(8)

公式(8)中a表示类名相似度的权重,1-a表示方法名相似度的权重.

4 实验分析

4.1 实验数据获取

本文采用的数据来自三个网上公开的代码评审项目,它们分别是QT*https://codereview.qt-project.org/、Android(AN)*https://android-review.googlesource.com和Open Stack(OP)*https://review.openstack.org/#/q/status:merged.每个项目开发时间均超过五年,评审流程已经非常地成熟稳定.三个项目的大部分评审数据都是公开的,均可以在网上获取.从三个项目网站中分别获取id连续的3万条数据,QT项目中id取150000-180000、AN项目中id取350000-380000、OP项目中id取350000-380000万.这些数据都是近期的,可以保证数据是有效的和稳定的.从预处理的数据中选取公开的并且已合并的数据进行统计,统计结果如表1所示:

从表2中可以看出,OP项目的开源评审次数是最多的,数据也是最丰富的,QT项目的评审次数和数据丰富程度次之,AN项目的最少.以QT项目为例,选取的数据时间从2016/02/22到2016/12/15,共有19504次公开的已合并的项目评审,在19504次项目评审中,共涉及到681位评审者和54687个文件,681位评审者共评审了代码修改51119次,评审了文件116664次,评审了72555次不同版本的代码修改.平均每次项目合并涉及到2.62次评审、5.98个文件和3.72个版本.

表1 实验数据统计

4.2 实验结果及分析

本文主要通过Top-k准确率和推荐平均准确率来对实验结果进行分析.对于公式(8)中的内容效力CE中a的取值,本文经过一部分实验选取其最优取值为0.76.

表2 TOP-K准确率对比

Top-k准确率表示算法推荐的前k名评审者的准确率.K越小,Top-k越高,表示推荐算法的推荐效果越好.当Top-1准确率为1时,表示算法总能推荐想要的结果,这是最理想的情况.给定一个推荐的评审者集合Rc和实际的评审者结合Rr,如公式(9)、公式(10),则Top-k准确率计算方法如公式(11)如示:

RC={r0,r1…ri},i=0,1,…k

(9)

Rr={r0,r1…ri},j=0,1,…n

(10)

(11)

如果实际评审者Rr中的前k名评审者包含推荐的第i名评审者ri,则isContain()函数返回1,否则返回0.根据文献[12],本文中选择k值为1、3、5.例如,Rr={a,b,c,d,e},Rc={a,c,f,b,e,d},则Top-1、Top-3、Top-5准确率依次为100%、66.7%和80%.

OP、QT和AN项目的Top-k准确率如表2所示.表2中共包含了四种方法OCRRM、REVIEWBOT、Number of Changes和Expertise Recommender(ER)在三个项目上的TOP-K值[11].本文模型OCCRM在三个项目上的Top-5准确率达到了63%、54%和58%,而ER的TOP-5准确率只有51%、53%和54%.从表中可以看出,在QT项目上的TOP-K准确率两者大致是相同的,而OP项目上的TOP-K准确率OCCRM模型更高.虽然在AN项目上的TOP-1和TOP-3是ER方法更好,但是TOP-5准确率仍是OCCRM方法更好,说明OCCRM模型能够有效地提高推荐准确率,尤其是推荐人数较多的时候.

推荐平均准确率表示推荐的专家中实际参加了评审的专家的比例.在统计三个实验项目的推荐平均准确率时,每进行10次评审者推荐统计一次推荐平均准确率.三个项目的推荐平均准确率如图2所示.

图2 OP、QT和AN的推荐平均准确率

从图2中可以看出,三个项目的推荐平均准确率在训练的初期因为数据的缺乏都很低.随着数据的丰富,推荐平均准确率迅速上升,达到收敛后在收敛准确率附近变化.OP项目的训练使用了约15%的评审数据,推荐平均准确率收敛后可以达到74.42%.QT项目的训练使用了约22%的评审数据,推荐平均准确率收敛后为64.63%.AN项目的训练使用了约34%的评审数据,推荐平均准确率收敛后为67.27%.而在文献[11]中,Expertise Cloud方法在三个项目上的平均准确率约为65.3%、60.3%和59.6%,Expertise Recommender方法的平均准确率约为58.8%、55.9%和58.5%.由此可见本文的OCCRM模型可以达到较高的推荐平均准确率,证明本文的方法有效.

5 结 语

基于评审历史的代码评审者推荐方法是代码评审的主要研究方向之一.本文提出的效力优化的代码评审者推荐模型OCRRM考虑了不同时期发生的历史评审数据对最终的推荐结果的影响,并且将历史评审数据提取为能够反映评审者评审具体内容和贡献的内容.在三个大型开源软件公开评审数据上的实验证明本模型能够有效的提高代码评审者的推荐准确率.虽然本文的实验数据很丰富,但是选取的数据都是三个项目中的连续的一部分,没有从头到尾的对一个项目完整的进行实验,以验证本模型在完整项目实验数据上的有效性.因此在后续工作中将进一步优化程序和验证完整的项目数据.

猜你喜欢

效力代码准确率
债权让与效力探究
乳腺超声检查诊断乳腺肿瘤的特异度及准确率分析
不同序列磁共振成像诊断脊柱损伤的临床准确率比较探讨
2015—2017 年宁夏各天气预报参考产品质量检验分析
颈椎病患者使用X线平片和CT影像诊断的临床准确率比照观察
神秘的代码
一周机构净增(减)仓股前20名
一行代码玩完19亿元卫星
近期连续上涨7天以上的股