日日操夜夜添-日日操影院-日日草夜夜操-日日干干-精品一区二区三区波多野结衣-精品一区二区三区高清免费不卡

公告:魔扣目錄網為廣大站長提供免費收錄網站服務,提交前請做好本站友鏈:【 網站目錄:http://www.ylptlb.cn 】, 免友鏈快審服務(50元/站),

點擊這里在線咨詢客服
新站提交
  • 網站:51998
  • 待審:31
  • 小程序:12
  • 文章:1030137
  • 會員:747

引用:Arianna Blasi, Alberto Goffi, Konstantin Kuznetsov, Alessandra Gorla, Michael D. Ernst, Mauro Pezzè, and Sergio Delgado Castellanos. 2018. Translating Code Comments to Procedure Specifications. In Proceedings of 27th ACM SIG- SOFT International Symposium on Software Testing and Analysis (ISSTA’18). ACM, New York, NY, USA, 12 pages. https://doi.org/10.1145/3213846.3213872.

摘要

過程規范在許多軟件開發任務中很有用。例如,在自動生成測試用例的過程中,它們可以指導測試,充當能夠發現錯誤并識別非法輸入的測試先知。盡管實際上很少有正式的規范,但是對于開發人員來說,使用半結構化注釋來記錄其代碼是標準做法。這些注釋通過預定義標簽和自然語言的組合來表達過程規范。本文介紹了 Jdoctor,該方法結合了模式,詞法和語義匹配,將 JAVAdoc 注釋轉換為以 Java 表達式編寫的可執行過程規范。在實證評估中,將 Javadoc 轉換為過程規范時,Jdoctor 的精度達到 92%,召回率達到 83%。

我們還將 Jdoctor 衍生的規范提供給自動測試用例生成工具 Randoop。規范使 Randoop 能夠生成測試案例,從而減少誤報并揭示更多缺陷。

1 簡介

程序規范表達了預期的程序行為,因此可以啟用或自動化許多軟件工程任務。在軟件測試中,它用作確定哪些輸入合法和哪些輸出正確的預言 [4, 17, 31, 37]。在調試中,它標識錯誤的語句 [29, 54]。在代碼合成中,這是合成器致力于的目標 [28, 47]。在重構中,它確保轉換是一致的 [23]。在形式驗證中,它區分正確和錯誤的實現 [53]。在運行時監視中,它可以識別異常行為 [15]。自動化(部分)任務需要工具可以操縱的機器可讀格式。正式的規范很好地達到了這個目的。但是,很少有正式的規范,因為編寫規范不是常見的軟件開發實踐。

? 相比之下,非正式規范很容易以自然語言編寫的半結構化和非結構化文檔的形式提供。程序員在過程文檔中指定前提條件、后置條件和特殊行為是標準做法。 Javadoc 標記語言和工具于 1995 年在 Java 的第一個版本中出現,而類似但跨語言的工具 Doxygen 在 2 年后出現了。 Java IDE 會自動插入 Javadoc 注釋的模板。最重要的是,程序員已經習慣于編寫這些注釋。結果,大量代碼包含了非正式的 Javadoc 規范。但是,軟件工程工具很少使用這些非正式規范。

? 本文介紹了 Jdoctor,它是一種從程序員已經創建的工件(即 Javadoc 代碼注釋)自動構建可執行過程規范的技術,而無需程序員更改開發實踐或做額外的工作??蓤绦幸幏妒强梢詧绦械囊幏?,例如,因為它是用編程語言而不是其他某種邏輯編寫的。它也需要在過程上表達,而不是(例如)聲明性地要求某些值的存在而不指示如何計算它。由 Jdoctor 生成的過程規范可用于多種軟件工程任務中,例如自動生成測試用例,如本文所示。

1.1 應用:測試用例生成

自動生成測試用例可以降低開發成本和軟件故障的社會成本 [5, 27, 44]。要自動生成測試用例,測試生成器必須生成一個輸入,該輸入使被測程序執行某些操作,并生成一個 oracle 以確定程序是否正常運行。

? 創建準確的測試 Oracle 仍然是一個未解決的問題。正如我們現在所解釋的,這將導致測試生成器同時遭受錯誤警報(當被測程序正確時測試失?。┖湾e過警報(當被測程序有錯誤時測試通過)。例如,假設自動生成的測試中的方法調用引發了異常。拋出此異常并不一定意味著所測試的方法有錯誤。存在以下可能性:

(1)引發的異常實際上揭示了實現缺陷。一個示例是在主題程序中觸發斷言,或者以其他方式無法完成所請求的操作。

(2)拋出異常是預期的、期望的行為。一個示例是在不可變對象上調用變量時發生的IllegalOperationException

(3)引發的異常是允許的,但不是必需的行為。例如,如果二進制搜索例程的參數數組未排序,則其行為不確定。允許引發任何異?;蚍祷嘏c搜索到的元素是否在數組中不一致的結果。

在沒有規范的情況下,測試生成工具可以使用試探法來猜測給定行為是正確還是不正確。一種試探法是,如果某個方法的參數之一為null,則以NullPointerException結尾的方法執行被認為是正確的,而不管是否可能將其視為可接受行為的特定要求 [40]。另一試探法是使用回歸預言,它認為正確的行為是受測試軟件的早期版本所暴露,并且認為任何其他行為是錯誤的,即使其他行為也為軟件設計人員所接受 [19]。

? 這些猜測還會導致誤報或警報遺漏,其中該工具無法報告暴露出錯誤行為的測試。當調用應該引發異常但失敗時,或者調用引發異常但工具試探性地忽略該異常以避免錯誤警報時,可能會發生這種情況。

? 我們建議測試生成器應該利用通過 Jdoctor 自動生成的可執行過程規范來依賴程序員編寫的非正式規范??蓤绦羞^程規范可以充當 oracle,從而使自動生成的測試用例更加有效,并且可以避免生成由易于出錯的啟發式方法派生的無效測試用例,如第 6 節所述。

1.2 貢獻

本文記錄的研究工作的主要貢獻是 Jdoctor,它是一種將非正式 Javadoc 代碼注釋轉換為可執行過程規范的方法。這種方法是自然語言解析和模式,詞匯和語義匹配技術的新穎組合。第二個貢獻是該方法的開放源代碼實現,該方法可以復制本文中提到的實驗并執行其他實驗。第三個貢獻是對該方法的多次實驗評估,證實了該方法的準確性和實用性,從而減少了自動生成的測試報告的錯誤警報的數量。

? 我們通過實驗評估了 Jdoctor 將 Javadoc 注釋轉換為過程規范的準確性。 Jdoctor 的性能明顯優于其他最新方法。然后,我們證明 Jdoctor 不僅準確,而且在測試生成領域也很有用。與測試生成工具(Randoop)集成后,Jdoctor 的規范可減少誤報。

2 代碼注釋分析

我們的工作受代碼注釋分析的啟發并重用了其中的想法。與我們的分析代碼注釋技術有關的最接近的工作是@ tComment [50]、ALICS [41]和 Toradocu [24]。 @tComment 使用模式匹配來確定與參數空缺有關的三種前提條件屬性。它可以達到很高的精度,并且可以召回與模式匹配的注釋,但是這些模式非常狹窄,并且不能一概而論。 ALICS 使用詞性標記,然后針對少量硬編碼名詞和術語進行模式匹配,從而根據代碼注釋生成過程前置條件和后置條件。同樣,可概括性一點也不明顯,并且需要為每個新域進行手動擴展。 Toradocu 是我們最初的工作,因此產生了 Jdoctor。它使用自然語言解析,并使用近似詞典序法匹配將識別出的名詞和動詞與任意程序表達式和運算進行匹配。 Toradocu 僅在特殊情況下起作用,這僅占 Javadoc 注釋的一小部分。 @tComment 和 Toradocu 都將其提取的屬性應用于測試生成問題。 ALICS 尚未應用于任何開發任務。

? Jdoctor 旨在結合并適當擴展這些技術中的最佳技術。模式匹配無法捕獲 Javadoc 標簽中自然語言的表現力和多樣性,即使僅在我們案例研究中的程序上進行評估也是如此。 Jdoctor 與自然語言解析一起對模式匹配進行了補充,ALICS 和 Toradocu 也是如此。但是,與以前的工作不同,Jdoctor 不僅限于特定注釋或規范的小語法,而且可以根據要分析的程序中定義的抽象來表達規范。與以前的所有工作不同,Jdoctor 添加了一種新穎的語義相似性概念。這樣處理的注釋使用的術語盡管在語義上是相關的,但與代碼中的標識符不同。

? 簡而言之,Jdoctor 會為各種過程行為生成規范:先決條件(與 Toradocu 不同)、常規后置條件(與@tComment 和 Toradocu 不同)和特殊后置條件(與@tComment 不同),并且比以前的工作更具通用性。與@tComment 不同,Jdoctor 不需要程序針對非法輸入遵守特定行為(對于@tComment,則為與 null 相關的行為)。與@tComment 和 ALICS 不同,Jdoctor 不僅限于特定注釋或規范的小語法,而且可以根據要分析的程序中定義的抽象表示規范。 Jdoctor 結合了文本模式匹配和自然語言處理(不同于@tComment),并引入了比 ALICS 和 Toradocu 更先進,更有效的新技術。與 ALICS 不同,Jdoctor 規范是可執行的,并且涉及數據結構,例如數組和集合以及數學表達式。

3 啟發性的 Javadoc 例子

Java 開發人員的標準做法是使用 Javadoc 注釋形式的非正式規范對代碼進行注釋。 Javadoc 工具會根據此類注釋自動生成 html 格式的 API 文檔。 Javadoc 注釋由自由格式的文本組成,其中一些前面帶有“標簽”:用于前提條件的@param標簽以及分別用于常規后置條件和異常行為的@return@throws標簽。現在,我們介紹一些例子。 從流行的開放源代碼 Java 代碼中摘錄的 Javadoc 注釋的示例,以及 Jdoctor 產生的輸出,以突出顯示此工作的挑戰以及先前工作的局限性。

3.1 前置條件

@param標記可表征方法參數并聲明調用者必須遵守的前提條件。 考慮以下注釋,該注釋來自 google Guava 的BloomFilter類。 Jdoctor 將此注釋轉換為可執行規范,該規范顯示在 Javadoc 注釋下方的框中。 這些子句與 Java 條件運算符“和”(&&)結合在一起以形成完整的過程規范。

將代碼注釋轉換為過程規范

 

? Jdoctor 使用數學表達式(第二和第三@param注釋)和復合條件(第三@param注釋)正確處理注釋。 Jdoctor 還了解到,有關第一個參數的注釋未指定任何前提條件,因此不會產生有關參數漏斗的任何說明。

3.2 特殊的后置條件

@throws@exception標記表示特殊執行的后置條件。 讓我們考慮以下來自 Apache Commons Collections 庫的ClosureUtils類的摘錄。

將代碼注釋轉換為過程規范

 

? 第一個特殊的后置條件很簡單,并且可以使用最新技術進行處理。 但是,只有 Jdoctor 能夠理解與容器中元素相關的屬性,如第二條@throws注釋中所示。

? Jdoctor 還處理更復雜的注釋,例如以下注釋,該注釋來自 Apache Commons Collections 庫的CollectionUtils類:

將代碼注釋轉換為過程規范

 

盡管此注釋描述的是無效條件,但現有技術無法產生正確的斷言。 Jdoctor 確定“兩個集合”均指參數ab,“比較器”指參數c

3.3 普通后置條件

@return標記表示方法定期執行的后置條件,并且變化最大,因此最具挑戰性。 這是三個其他技術無法處理的示例。

? 第一個示例來自 Apache Commons Collections 庫中的BagUtils類:

將代碼注釋轉換為過程規范

 

? Jdoctor 使用在類Bag中聲明的常量產生后置條件。 將代碼注釋與要測試的代碼中的方法或其他代碼元素匹配并不總是那么簡單,正如以下針對JGraphT庫的Graph.addEdge()方法的注釋所說明的那樣。

將代碼注釋轉換為過程規范

 

? Jdoctor 推斷“此圖”是指圖實例本身,并且containsEdge方法可以檢查后置條件。 Jdoctor 正確傳遞兩個頂點作為此方法的參數以形成邊。

? 將代碼注釋與代碼元素匹配可能還需要一些語義相似性概念。 從同一個 Graph 類中獲取以下示例。

將代碼注釋轉換為過程規范

 

? 由于 Jdoctor 新穎的語義相似性分析,Jdoctor 推斷“未找到”在語義上與“容器中包含一個元素”的概念有關。 @tComment 和 Toradocu 缺乏任何語義相似性分析,而 ALICS 僅支持有限數量的手動定義同義詞。

4 JDOCTOR

Jdoctor 將與構造函數和方法有關的 Javadoc 注釋轉換為可執行的 Java 表達式。它的主要見解是觀察到,自然語言注釋中的名詞傾向于與代碼中的變量或表達式相對應,注釋中的動詞/謂詞與操作或方法相對應。 Jdoctor 處理 Javadoc 前置條件(@param)、普通后置條件(@return)和特殊后置條件(@throws@exception)。

Jdoctor 的工作分為四個步驟:

(1)文本規范化(第 4.1 節):Jdoctor 對 Javadoc @ param、@ return、@ throws@exception塊標記中的文本進行預處理,以準備分析自然語言。此階段包括幾個文本轉換,以方便后續步驟。

(2)命題識別(第 4.2 節):Jdoctor 使用自然語言解析器來識別注釋中每個子句的命題(主語-謂詞對)。

(3)命題翻譯(第 4.3 節):Jdoctor 將每個識別的命題與 Java 元素(例如表達式或操作)匹配。此步驟是 Jdoctor 的核心,它依賴于模式,詞匯和語義相似性匹配的組合。

(4)創建規范:Jdoctor 創建 Java 布爾表達式,該表達式對自然語言 Javadoc 注釋進行編碼。它用 Java 代碼替換文本中的每個主題和謂詞,并遍歷解析樹以創建合法的 Java 代碼,包括方法調用,操作和布爾連接符(來自語法連接)。

4.1 文本規范化

Javadoc 注釋很少是語法上完整的英語句子。例如,他們經常缺乏標點符號,具有隱含的主語和/或動詞,并且將數學符號與英語混在一起。當前的 NLP 解析器不能總是處理程序員編寫的 Javadoc 注釋樣式。 Jdoctor 通過在使用 NLP 解析器之前將其預處理為語法英語句來使文本可解析。這個階段適當地擴展了先前的工作,并允許處理更多的 Javadoc 注釋。

? 標點符號:Jdoctor 會在缺少句號時添加一個句號。它還消除了初始標點符號,這些標點符號是由于程序員(錯誤地)使用 Javadoc 注釋中的逗號將參數或異常名稱與其描述分開而產生的。

? 隱式主語:評論可能引用事先提及的主語。例如,典型的@param注釋是“永遠不會為空”。由于 Jdoctor 孤立地分析句子,因此每個句子都需要一個明確的主題。對于@param注釋,Jdoctor 在注釋文本的開頭添加參數名稱。 Jdoctor 還啟發式地解析代詞(例如“ it”),將其替換為注釋中最后使用的名詞。

? 隱式動詞:某些注釋具有隱式動詞,例如“ @ param num,a positive number”。 Jdoctor 會根據被認為是主語的第一個名詞是單數還是復數來添加“is”或“are“。

? 句子不完整:如果沒有主從句,Jdoctor 會將從屬從句轉換為主從句。

? 詞匯標準化:為了適應以后的模式匹配,Jdoctor 標準化了與 null、if 和 empty 模式有關的文本。例如,Jdoctor 將“ non-null”和“ nonnull”標準化為“ not null”。

? 數學符號:Jdoctor 將不等式轉換為可以解析為形容詞的占位符。例如,如果{@code e} <0,則 Jdoctor 將子句轉換為表達式 e <0,并進一步轉換為 e is LT0。

4.2 命題識別給定一個英語句子,Jdoctor 會識別<主語,謂語>對,也稱為命題 [14],以及連接命題(如果有)的連接詞或析取詞。從自然語言句子中提取<主語,謂語>對稱為開放信息提?。∣IE)[1, 14, 18, 46]。

? Jdoctor 首先執行部分 POS 標記 [41]。它將參數名稱標記為名詞,將不等號占位符(例如 LT0)標記為形容詞。 Jdoctor 通過 Stanford Parser [34]完成 POS 標記過程,該過程產生代表輸入語句的語義圖(豐富的分析樹)。語義圖的節點對應于句子的單詞,邊緣對應于單詞之間的語法關系。

? Jdoctor 根據句子結構和圖中編碼的語法角色,識別構成主題的單詞和構成謂詞的單詞。更精確地講,給定在語義圖中被標記為主題的單個節點(即單詞),Jdoctor 通過訪問以主題節點為根節點的子圖并收集涉及復合類型關系的所有單詞來識別完整的主題短語、狀語修飾語、形容詞修飾語、確定語和名詞修飾語。這與 ALICS [41]完全不同,ALICS 僅使用由 Stanford Parser 提供的即用型 POS 標記,因此缺少所有其他詞的信息。 Jdoctor 通過收集具有以下語法關系的單詞來識別謂語:助詞、系詞、合詞、直接賓語、開放式補語以及形容詞、否定詞和數字修飾語。

? Jdoctor 從簡單句子中提取一個命題,從多子句中提取多個命題。通過處理語義圖中諸如“和”和“或”之類的語法連接的專用邊緣,Jdoctor 可以正確支持多子句。在遍歷圖時,Jdoctor 會確定與正確的布爾連詞或析取詞相互關聯的命題,這些命題反映了輸入句子中的語法連詞。

4.3 命題翻譯

Jdoctor 通過連續應用模式匹配(第 4.3.1 節)和詞匯匹配(第 4.3.2 節)的補充啟發式方法并結合語義相似性分析(第 4.3.3 節)來翻譯每個命題。 Jdoctor 使用第一個能翻譯成功的方法。

? 本節描述單個命題的翻譯。 Jdoctor 通過根據輸入注釋中的語法連接(“或”,“和”)合并組件命題的翻譯來處理多個命題。

? 算法 1 顯示 Jdoctor 如何處理 Javadoc 注釋的(規范化)文本。文本可能包含多個命題。該算法獨立地翻譯每個命題。然后,將這些翻譯(它們是 Java 表達式和操作)重新組合以創建完整的可執行規范。對@return注釋會進行特殊重組。 Jdoctor 首先確定 guard、true 屬性和 false 屬性。例如,Apache Commons Collections 中ArrayStack.search()的返回注釋是“對象堆棧中從 1 開始的深度,如果找不到,則為-1”。 Jdoctor 將“如果未找到”標識為 guard 對象,將“從對象的堆棧開始的基于 1 的深度”標識為 true 屬性,即,當 guard 為 true 時保留的屬性,而將“ -1”標識為 false 屬性,即將 guard 評估為 false 時保留的屬性。

將代碼注釋轉換為過程規范

 

? 將命題轉換為 Java 表達式時(第 15 行),Jdoctor 嘗試匹配每個主題并斷言為代碼元素。從直覺上講,名詞對應于對象,在源代碼中以表達式表示對象,而動詞對應于動作或謂詞,在源代碼中以操作符表示。

? Jdoctor 首先分析命題的主題(第 17 行),然后嘗試將該主題與代碼元素進行匹配,該代碼元素可以是方法的參數,類的字段或類本身。 Jdoctor 檢索范圍內所有代碼元素的標識符和類型作為候選者,并尋找最佳匹配。例如,當在第 3 節中處理注釋“如果比較器為空”時,Jdoctor 將主題“比較器”與類型為Comparator的方法的參數匹配。 Jdoctor 通過詞法匹配來實現此任務,我們將在 4.3.2 節中對此進行說明。

如果 Jdoctor 找到主題的匹配表達式,它將繼續尋找相應的匹配謂詞(例如示例中的“ is null”)。更詳細地講,Jdoctor 檢索主題范圍內所有公共方法和字段的代碼標識符,以作為可能的候選者。例如,在將主題比較器匹配為Comparator類型之后,Jdoctor 檢索公共方法的完整列表和Comparator類的字段作為可能的候選對象。一旦確定了可能的候選者,Jdoctor 就會逐步利用一組啟發式方法來推斷可能候選者中謂詞與代碼元素的正確匹配:(i)檢查謂詞是否與一組預定義翻譯(行)匹配 22),(ii)查找詞匯相似的匹配項(第 24 行),(iii)根據語義相似性搜索匹配項(第 27 行)。

? 4.3.1模式匹配。 Jdoctor 使用模式匹配將常見短語(例如“是正”,“是負”和“是空”)映射到 Java 表達式片段> 0,<0 和== null。與以前的工作一致 [41, 51, 55],Jdoctor 采用了一組可擴展的模式,這些模式涵蓋了原始類型、字符串和無效性檢查的屬性。模式匹配可以有效地轉換常見模式,但不能處理特定于域的概念或特定于代碼的行話,例如“如果在圖中找不到頂點”中的概念“頂點”和“圖形”。

? 4.3.2詞法匹配。 Jdoctor 會根據直覺認為 Javadoc 注釋中的單詞在詞法上類似于代碼元素,從而嘗試將主題或謂詞與相應的代碼元素進行匹配。 Jdoctor(i)根據駝峰案例慣例將代碼候選詞標記化為單獨的術語,(ii)計算每個詞與主題/謂詞中每個單詞之間的 Levenshtein 距離,(iii)選擇 Levenshtein 距離最小的候選詞,只要不超過閾值即可(默認閾值非常小(即兩個),以盡可能避免錯誤匹配)。例如,在處理第 3 節中出現的注釋“如果比較器為空”時,Jdoctor 將主題“比較器”與方法類型為距離為 0 的比較器的參數進行匹配。

Jdoctor 使用詞法匹配的方式類似于 Toradocu [24]。這項技術優于簡單的模式匹配(例如@tComment 實現的模式匹配)和簡單的自然語言處理(例如 ALICS 中實現的模式)。它的局限性是基于這樣的假設,即 Javadoc 注釋中的名詞應與代碼中的標識符相似,但實際上并不總是如此。

? 4.3.3語義匹配。為了說明模式和詞法匹配的限制,請考慮謂詞“在圖中未找到”。所需的轉換為!graph.containsVertex(vertex)。模式匹配僅在有特定模式可用于處理這種情況時才有效。詞法匹配失敗,因為代碼元素containsVertex在詞法上與注釋中出現的“在圖中找不到”相近。 Jdoctor 語義匹配方法建立在以下觀察的基礎上,即語法上不同的術語可能具有緊密的語義。例如,代碼中的方法containsVertex和注釋中的“在圖形中找不到”的概念在詞法上是不同的,盡管它們的語義是相關的。由于單詞之間的語義相似性,Jdoctor 能夠處理模式匹配和詞法匹配都失敗的情況。 Jdoctor 使用單詞嵌入,這已被證明是表示語義單詞關系的強大方法。它將單詞嵌入到高維向量空間中,以使單詞之間的距離與語義相似性緊密相關,而與語法差異無關。 Jdoctor 為此使用了兩層神經網絡模型 GloVe。

? Jdoctor 從謂詞中刪除自定義的停用詞列表,并在使用 GloVe 計算語義相似度之前應用詞形還原。詞形還原將術語轉換為它們的原形,例如,“playing”和“played”變為“play”,以減少域中術語的數量來簡化語義匹配。默認情況下,Jdoctor 使用停用詞列表,其中包括屬于 Java 語言的冠詞和單詞,例如“ for”,“ do”和“ null”。但是,Glove 模型本身只能捕獲單個術語的語義相似性。因此,它將報告語義上相關的術語“頂點”和“圖形”。但是,大多數情況下,謂詞和代碼標識符由多個單詞組成。例如,在JGraphT中,注釋摘錄“找到了頂點”應與方法containsVertex相匹配。為了一次比較多個單詞,Jdoctor 使用了單詞移動器的距離(WMD)算法 [30]。

? WMD 測量兩個文本片段之間的語義距離,因為注釋中的所有單詞(在這種情況下為[vertex,is, found])必須與代碼元素標識符中的單詞(在這種情況下為[contain,vertex])中的單詞完全相同。與 Jdoctor 進行詞法匹配時類似,它會選擇給定閾值內語義距離最接近的候選詞。

? 盡管提供了不同的匹配策略,但 Jdoctor 僅對主語匹配使用詞法相似性。這種方法迫使 Jdoctor 將主語與具有很高精確度的代碼元素進行匹配(盡管它可能會丟失一些匹配項)。這種保守的決定對于 Jdoctor 的性能至關重要,因為主語匹配為以后匹配謂詞提供了范圍。更廣泛的(可能是錯誤的)范圍將使謂詞匹配的搜索指向完全錯誤的路徑。

? Jdoctor 生成單個 Java 布爾條件作為@param注釋的翻譯,并生成一對“預期的異常類型,Java 布爾條件”作為@throws注釋的翻譯。 @return注釋的翻譯不是 Java 的布爾值;取而代之的是,單個轉換由對應于 guard、true 和 false 屬性的三個 Java 布爾條件組成。

5 評估:翻譯準確性

我們通過回答以下研究問題來評估 Jdoctor 的翻譯準確性。

? RQ1 在將 Javadoc 注釋轉換為過程規范時,Jdoctor 的有效性(準確率和召回率)如何?

? RQ2 Jdoctor 的有效性與最新方法@tComment 和 Toradocu 相比如何?

? 我們根據準確率和召回率(信息檢索任務的標準指標)來衡量有效性,例如將 Javadoc 注釋翻譯為過程規范。

? 準確率衡量正確輸出相對于缺失和錯誤輸出的比例。當 Jdoctor 產生與預期規范匹配的規范時,輸出正確(C)。當 Jdoctor 不產生任何規范時,輸出丟失(M)。當 Jdoctor 在沒有預期的規格(W1)或與預期的規格不匹配的規格(W2)產生規格時,輸出錯誤。準確率定義為正確輸出數與輸出總數之間的比率:

將代碼注釋轉換為過程規范

 

? 召回率衡量工具產生的期望輸出的比例,它定義為正確輸出的數量與期望輸出的總數之間的比率:

將代碼注釋轉換為過程規范

 

? 我們的評估保守地認為部分正確的翻譯是錯誤的。 例如,如果注釋為“@throws Exception如果x為負或y為空”,則翻譯“ x <0”被視為錯誤。

5.1 實驗設置

為了進行評估,我們選擇了 6 個維護良好的開源 Java 系統(請參閱表 1)。對于每個系統,我們(i)丟棄沒有文檔或文檔數量有限的類,即 Javadoc 注釋少于 5 個,以及(ii)忽略注釋了從java.lang.Object繼承的方法、getter 和 setter(其名稱為方法的注釋)以“ get”或“ set”開頭)。表 1 中的“文檔班級”列報告了滿足每個學科這些條件的班級數。

? 然后,我們選擇并手動分析了至少 10%的已記錄類和方法:分別在“已分析類”和“已分析方法”列中。為此,我們應用了 PPS(概率正比于規模)抽樣方法,選擇每個類別的概率與該類別中的方法數量成正比。對于每個選定類中的每個分析方法,我們手動確定其基本事實-將 Javadoc 注釋正確轉換為可執行方法規范。為此,我們閱讀了用英語表達的 Javadoc 注釋,并編寫了與每個@ param、@ return、@ throws@exception標記相對應的可執行規范。至少有兩位作者獨立審查了每種翻譯。

? 有時,與 Javadoc 標記對應的文本不能表示為可執行規范。一個示例是“如果在讀取文件時遇到問題,則@throws IOException”。對于此類注釋,我們不希望 Jdoctor 產生任何輸出。我們丟棄了不包含任何可轉換為可執行規范的注釋的類,即不屬于已分析類的列表。這給我們留下了 118 個分析過的類和 829 個 Javadoc 注釋,我們為它們手動生成了真實的可執行規范。我們的實驗比較了三種工具,所有這些工具均由程序員編寫的非正式英語規范來創建可執行過程規范。

l @tComment [50]與三種不同類型的無效性規范的預定模板匹配。我們希望使用@tComment 實現,但是由于文檔數量有限而無法使用(例如,其文件格式未記錄)。我們發現,更容易根據發布的描述重新實現@tComment [50]。我們實現的@tComment 取得了與本文相似的結果,并公開供外部檢查。

l Toradocu [24]通過 NLP 和字符串匹配的組合,從@throws 注釋中生成特殊的后置條件。我們使用了來自 GitHub 的 Toradocu 實現。

l Jdoctor 是本文描述的工具。我們沒有在比較中考慮 ALICS [42],因為即使在作者的支持下,我們也無法使該工具正常運行(有關此問題的更多信息,請參見第 8 節)。而且,ALICS 沒有產生可執行的規范,因此很難進行比較。

5.2 準確度結果 (RQ1, RQ2)

表 2 報告了@ tComment、Toradocu 和 Jdoctor 在表 1 的主語類上的準確性。如第 2 節所述,Toradocu 不處理先決條件,Toradocu 和@tComment 都不處理正常的后置條件(表中的值 n.a. )。表格中的數據表明,Jdoctor 的精度可與最新方法相媲美,而 Jdoctor 的召回率遠高于最新方法。

將代碼注釋轉換為過程規范

 

前置條件。 Jdoctor 處理不同類型的前置條件,而@tComment 僅處理通過簡單分析處理的與 null 相關的檢查。 @tCom 的精度比 Jdoctor 更高,這得益于其模式的特殊性,例如“may be null”,“must not be null”和“ @throws IllegalArgu.mentException if...is null”。但是,對@tComment 的簡單分析會錯過許多翻譯,導致召回率比 Jdoctor 低得多。

正常的后置條件。 Jdoctor 是唯一足以表達@return注釋的方法。由于常見返回條件的復雜性,@return注釋的精度和召回率均低于其他標記。例如,注釋“ @return 排序了的數組”聲明后置條件為檢查例程返回的數組是否已排序。該檢查涉及對陣列的循環,在 Jdoctor 的當前實現中不支持此檢查。其他難以檢查的條件是,例如 Commons Math 中的FastMath類中的注釋“ @return n + 1,如果沒有發生溢出”,其警衛應檢查是否發生了溢出。精度和召回率相對較低的另一個原因是后置條件通常包括兩個或多個元素之間的比較。目前,Jdoctor 假定主題和謂詞轉換為單個 Java 元素,并且無法處理更復雜的情況,例如“如果ac的大小差不等于 1”,“如果最大迭代次數小于或等于最小迭代次數”和“如果xvalyval大小不同”。

特殊的后置條件。與@tComment 相比,Jdoctor 具有更好的精度和召回率。 @tComment 僅翻譯與空相關的注釋,即在特定上下文中包含單詞“空”的注釋。例如,Jdoctor 可以翻譯表達式“ aString 不為空”,而@tComment 則不能。在分析復雜的句子時,Jdoctor 的句子分析比@tComment 的模式匹配更有效。 Jdoctor 可以翻譯由許多從句與特定的語法連接相聯系的從句組成的句子,例如xy為正或z為負,而@tComment 的模式匹配則不然。 Jdoctor 比 Toradocu 具有更好的精度和召回率。 Jdoctor 的更好結果歸功于更精確的算法,可以將主語和謂詞轉換為 Java 元素,并獲得了更多受支持的注釋集(請參見第 4 節)。

? 92%的整體精度和 83%的召回率支持對 RQ1 的肯定回答:Jdoctor 在將 Javadoc 注釋轉換為過程規范方面有效且準確。我們的評估還支持對 RQ2 的肯定回答:與最先進的技術@tComment 和 Toradocu 相比,Jdoctor 的準確率更高。

5.3 不一致的規范

通過檢查每個 Javadoc 注釋的 Jdoctor 輸出,我們手動檢查了第 5.2 節中報告的 Jdoctor 的準確性。檢查表明 Jdoctor 可以產生正確但不一致的規范。盡管目前只能通過手動分析 Jdoctor 的輸出來找到許多這些問題,但我們計劃擴展該工具以自動報告它們。現在,我們描述我們遇到的許多不一致之處。我們發現,許多開發人員編寫的規范在邏輯上是不一致的-也就是說,它們無法實現或不能被客戶端使用。這突出了將非正式的英語規范轉換為可執行形式的附帶好處:可執行形式中的不一致性比非正式表述并不明顯,并且可以自動檢查機器可讀的規范。下面我們報告 Jdoctor 可能突出顯示的六類不一致和錯誤。

? 一些規范會轉換為并非總是定義良好的表達式,因為它們的求值可能會引發異常。例如,當 arg 為 null 時 arg.f> 0,這可能導致兩種合理但不同的解釋:arg.f 表達式始終具有一個值(即 arg!= null && arg.f> 0)或條件只要 arg.f 具有值(即 arg!= null || arg.f> 0),則為 true。兩種解釋都在實踐中出現,盡管它們的含義對于客戶和實施者而言都大相徑庭。

? 許多規范具有沖突的前提條件和后置條件。 Commons Collections 中的CollectionUtils類的一個簡單示例是

@param a第一個集合,不能為null

@throws NullPointerException 如果anull

@throws子句指的是違反@param子句的情況,導致兩種規則上的解釋,盡管相互矛盾:(i)方法的域是所有值(允許程序員傳遞null),并承諾當傳入null時會發生什么,或(ii)該域都是非空值,程序員不應傳遞空值。兩種解釋都是合理的,并且沒有辦法知道設計者的意圖,但兩者之間的區別是微不足道的:前者指出,維護者不得在將來更改實施,而后者則規定實施者可以在將來的實現中自由更改,依賴異常的客戶代碼將可能出錯。

? 一些規范指示給定條件的多個結果。例如,讓我們考慮

@throws NullPointerException 如果arg1null

@throws IllegalArgumentException 如果arg2為負數

如果arg1nullarg2為 0,則該例程需要同時拋出NullPointerExceptionIllegalArgumentException,這在 Java 中是不可能的。沒有注意到不一致的客戶可能會遇到意外的行為。這種不一致性的一個例子是JGraphTKShortestPaths類。后置條件中也會出現類似的不一致之處。

? Jdoctor 自動識別 Javadoc 中的一些很可能是由于復制和粘貼錯誤引起的錯誤[6]。例如,Guava 19.0 中CharMatcher.matchesNoneOf方法的文檔指出:“如果此匹配器匹配序列中的每個字符(包括序列為空時),則返回 true”,同時應指出該方法不匹配序列中的任何字符。 Jdoctor 將拼寫錯誤“匹配每個字符”正確轉換為使用方法matchAllOf的 Java 表達式,并且此斷言在運行時失敗,突出顯示了不正確的 Javadoc。

? 某些過程的 Javadoc 引用了不正確的形式參數名稱。常見的原因是 Javadoc 從重寫的實現中繼承,并伴隨著形式參數名稱的更改。 HTML API 文檔的讀者會在 Javadoc 中看到一組名稱,在方法名稱中看到另一組名稱。通常,這種對應是顯而易見的,但并非總是如此,讀者不必推論它。

? Jdoctor 還自動在 Javadoc 中報告了一些拼寫錯誤。例如,在 GraphStream 項目的Node類中,Javadoc 錯誤地說方法可能拋出IndexOutOfBoundException,而不是正確的IndexOutOfBoundsException。 Jdoctor 可能會報告問題,因為它沒有在其類路徑中找到類IndexOutOfBoundException。

分享到:
標簽:注釋 代碼
用戶無頭像

網友整理

注冊時間:

網站:5 個   小程序:0 個  文章:12 篇

  • 51998

    網站

  • 12

    小程序

  • 1030137

    文章

  • 747

    會員

趕快注冊賬號,推廣您的網站吧!
最新入駐小程序

數獨大挑戰2018-06-03

數獨一種數學游戲,玩家需要根據9

答題星2018-06-03

您可以通過答題星輕松地創建試卷

全階人生考試2018-06-03

各種考試題,題庫,初中,高中,大學四六

運動步數有氧達人2018-06-03

記錄運動步數,積累氧氣值。還可偷

每日養生app2018-06-03

每日養生,天天健康

體育訓練成績評定2018-06-03

通用課目體育訓練成績評定