新聞中心
曾經(jīng)為大家相信介紹過10款常用Java測試工具,代碼覆蓋率工具這項軟件測試過程中使用的一個重要的工具卻從來沒介紹過,來為Java?程序生成測試的覆蓋率結(jié)果,并提供了關(guān)于怎樣分析結(jié)果以改進測試的信息。本文向您展示了怎樣使用IBM一款開發(fā)工具(IBM? Rational? Application Developer)中提供的代碼覆蓋工具如何來為Java?程序生成測試的覆蓋率結(jié)果。

創(chuàng)新互聯(lián)服務(wù)項目包括昌江黎族網(wǎng)站建設(shè)、昌江黎族網(wǎng)站制作、昌江黎族網(wǎng)頁制作以及昌江黎族網(wǎng)絡(luò)營銷策劃等。多年來,我們專注于互聯(lián)網(wǎng)行業(yè),利用自身積累的技術(shù)優(yōu)勢、行業(yè)經(jīng)驗、深度合作伙伴關(guān)系等,向廣大中小型企業(yè)、政府機構(gòu)等提供互聯(lián)網(wǎng)行業(yè)的解決方案,昌江黎族網(wǎng)站推廣取得了明顯的社會效益與經(jīng)濟效益。目前,我們服務(wù)的客戶以成都為中心已經(jīng)輻射到昌江黎族省份的部分城市,未來相信會繼續(xù)擴大服務(wù)區(qū)域并繼續(xù)獲得客戶的支持與信任!
什么是Rational Code Coverage特性?
代碼覆蓋率是軟件測試的一個重要方面,對于一個構(gòu)件的總體系統(tǒng)測試來說可能是一個基本的參數(shù)。覆蓋工具背后的動機向您(作為開發(fā)員或者測試員)提供了關(guān)于代碼的一系列觀點,這些代碼在一系列的測試之中會得到檢查。該信息會非常的有用,因為您可以使用它來設(shè)計新的測試用例以獲得足夠的覆蓋范圍。
IBM? Rational? Code Coverage特性是一個與IBM? Rational? Application Developer相集成的工具。您可以使用它來生成并分析關(guān)于Java程序的覆蓋率統(tǒng)計數(shù)據(jù)。工具會為測試下的程序生成聲明覆蓋率統(tǒng)計數(shù)據(jù)(這就是說,執(zhí)行程序中行的數(shù)量與百分比)。
Rational Code Coverage特性現(xiàn)在只能獲得Rational Application Developer 7.5版本及其后續(xù)版本。本文假設(shè)您使用的是Rational Application Developer 7.5.4版本。對代碼覆蓋率而配置IBM? WebSphere?Application Server的部分假設(shè)您使用的是7.0版本,但是提供的指南的一些調(diào)整仍然適用于上述版本。
指南
為了適當?shù)胤治鯮ational Code Coverage特性中的覆蓋率統(tǒng)計數(shù)據(jù),理解場景背后所用到的技術(shù)是非常重要的。
Eclipse Test與Performance Tools Project(TPTP)中提供的Rational Code Coverage特性所使用的工具引擎。Probekit用于控制一個類的比特代碼,并引入覆蓋率數(shù)據(jù)收集引擎的通用訪問。圖1提供了關(guān)于這個過程的一個高層次的概述:
圖1.Rational Code Coverage執(zhí)行環(huán)境的概述
基本快與可執(zhí)行的單元
Probekit是一種在Eclipse平臺上的框架,并可以操作所謂可執(zhí)行單元的比特代碼。可執(zhí)行單元的定義與基本塊的傳統(tǒng)定義有輕微的不同,但是當您在分析結(jié)果時,您就需要去關(guān)注這點差異了。
根據(jù)定義,一個所謂的基本塊就是一系列的指南,這些指南不能再進行分支或者分散。這里的關(guān)鍵思想在于,當?shù)谝粋€指南運行的時候,該塊中隨后所有指南都一定會得到執(zhí)行而且不會得到中斷。接下來的是一個基本塊,它可以認為是一個單個組或者一系列的指南。通常來說,基本塊的結(jié)尾是branch,call,throw或者return聲明。
一個可執(zhí)行的單元由每一個基本快開始,而與每行源代碼相對應(yīng)的指南與前面版本中的指南有所不同??蓤?zhí)行的單元與基本塊的不同點,在于決定一個可執(zhí)行單元末尾的因素。例如,pide指南并沒有認為是一個可執(zhí)行單元的結(jié)尾,盡管有例外情況的存在。
Probekit是Rational Code Coverage特性所使用的,以將通用代碼引入到每一個可執(zhí)行的單元之中。結(jié)果來說,您可以定制Rational Code Coverage特性以向組成性(換句話說,就是塊覆蓋率)可執(zhí)行單元層次報告統(tǒng)計數(shù)據(jù)。為了知道這些工具是怎樣更改類了,您可以參考接下來的代碼清單1與代碼清單2。代碼清單1提供了未處理類的分解輸出(從javap工具來),同時代碼清單2為處理過的類提供了分解輸出。注意代碼清單2中italics的行就是作為處理步驟一部分導入的代碼部分。
#p#
清單1.未處理的類文件
- Compiled from "Part.java"
- public class com.ibm.storeapp.models.Part extends java.lang.Object{
- public com.ibm.storeapp.models.Part(int);
- Code:
- 0: aload_0
- 1: invokespecial #15; //Method java/lang/Object."
":()V - 4: iload_1
- 5: bipush 10
- 7: if_icmple 18
- 10: aload_0
- 11: iload_1
- 12: invokespecial #18; //Method setDiscountedPrice:(I)V
- 15: goto 23
- 18: aload_0
- 19: iload_1
- 20: putfield #21; //Field price:I
- 23: return
- public int getPrice();
- Code:
- 0: aload_0
- 1: getfield #21; //Field price:I
- 4: ireturn
- }
清單2.每一個可執(zhí)行單元處理的類文件
- Compiled from "Part.java"
- public class com.ibm.storeapp.models.Part extends java.lang.Object{
- public com.ibm.storeapp.models.Part(int);
- Code:
- 0: ldc #49; //String com/ibm/storeapp/models/Part 2: iconst_0 3: iconst_0 4:
- invokestatic #48; //Method llc_probe$Probe_0._executableUnit:(Ljava/lang/String;II)V
- 7: aload_0
- 8: invokespecial #15; //Method java/lang/Object."
":()V - 11: ldc #49; //String com/ibm/storeapp/models/Part 13: iconst_0 14: iconst_1 15:
- invokestatic #48; //Method llc_probe$Probe_0._executableUnit:(Ljava/lang/String;II)V
- 18: iload_1
- 19: bipush 10
- 21: if_icmple 46
- 24: ldc #49; //String com/ibm/storeapp/models/Part 26: iconst_0 27: iconst_2 28:
- invokestatic #48; //Method llc_probe$Probe_0._executableUnit:(Ljava/lang/String;II)V
- 31: aload_0
- 32: iload_1
- 33: invokespecial #18; //Method setDiscountedPrice:(I)V
- 36: ldc #49; //String com/ibm/storeapp/models/Part 38: iconst_0 39: iconst_3 40:
- invokestatic #48; //Method llc_probe$Probe_0._executableUnit:(Ljava/lang/String;II)V
- 43: goto 58
- 46: ldc #49; //String com/ibm/storeapp/models/Part 48: iconst_0 49: iconst_4 50:
- invokestatic #48; //Method llc_probe$Probe_0._executableUnit:(Ljava/lang/String;II)V
- 53: aload_0
- 54: iload_1
- 55: putfield #21; //Field price:I
- 58: ldc #49; //String com/ibm/storeapp/models/Part 60: iconst_0 61: iconst_5 62:
- invokestatic #48; //Method llc_probe$Probe_0._executableUnit:(Ljava/lang/String;II)V
- 65: return
- public int getPrice();
- Code:
- 0: ldc #49; //String com/ibm/storeapp/models/Part 2: iconst_2 3: iconst_0 4:
- invokestatic #48; //Method llc_probe$Probe_0._executableUnit:(Ljava/lang/String;II)V
- 7: aload_0
- 8: getfield #21; //Field price:I
- 11: ireturn
- static {}; Code: 0: ldc #49; //String com/ibm/storeapp/models/Part 2: ldc #55;
- //String Part.java 4: ldc #57; //String
(I)V+setDiscountedPrice(I)V - +getPrice()I 6: ldc #59; //String #10+11032,301,3 8: invokestatic #54;
- //Method llc_probe$Probe_0._staticInitializer:
- (Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;)V 11: return
- }
在Rational Application Developer中生成覆蓋率統(tǒng)計數(shù)據(jù)
Rational Code Coverage特性的一個主要的優(yōu)勢在于,您可以通過切換到項目Properties的Code Coverage窗格,來將其在Rational Application Developer中的Java項目上激活,如圖2所示。
圖2.項目Properties中的代碼覆蓋窗格
#p#
選擇圖2中的Enable code coverage復(fù)選框以激活項目的代碼覆蓋率,并評價覆蓋下項目的類。您還可以使用該窗格來定制可接受的覆蓋率層次。接下來描述了組合的支持層次:
◆類型覆蓋率:一個類中覆蓋的類型百分比
◆方法覆蓋率:一個類中覆蓋的方法百分比
◆行覆蓋率:類文件中覆蓋的行百分比
◆塊覆蓋率:一個類文件中覆蓋的塊的百分比。注意一個塊會參考一個可執(zhí)行的單元(如以前描述的那樣)
您還可以指定通用的篩選規(guī)則,而且它們可以用于控制在項目中評價哪些內(nèi)容。默認條件下,項目中的所有類都會得到評價,但是您可以創(chuàng)建通用的篩選規(guī)則來排除目標包或者指定類型,如果您需要限制結(jié)果的話。
Package Explorer
在您激活一個項目中的代碼覆蓋率以后,覆蓋率統(tǒng)計數(shù)據(jù)就會在下一次程序啟動的時候生成。注意不是所有類型啟動配置都會自動生成統(tǒng)計數(shù)據(jù)。表1顯示了Rational Application Developer內(nèi)支持的啟動類型。
表1.支持的啟動配置
| 啟動類型 |
| Java Applet |
| OSGi框架 |
| JUnit |
| JUnit插件測試 |
| Java程序 |
| Eclipse程序 |
| 標準Widget Toolkit (SWT)程序 |
該程序是一個不同交通工具(汽車、貨車、摩托車等等)的簡單再現(xiàn)。圖3中是一個概括了該程序結(jié)構(gòu)的UML圖。
圖3.范例程序的UML圖
在項目中有兩種定義好的JUnit測試:TestCar.java與TestCarImproved.java。正如其名字所暗含的一樣,這些測試的目標是Car.java類。而在Rational Application Developer的Java視角中,您可以右擊TestCar.java并選擇Run As > JUnit test來啟動TestCar.java測試。JUnit測試的結(jié)果會正常顯示在JUnit視圖中。覆蓋率數(shù)據(jù)的結(jié)果會集成到Rational Application Developer UI中,而且您可以切換回Package Explorer來分析它們。圖4顯示了TestCar.java測試的一個范例結(jié)果。
圖4.Package Explorer中顯示的TestCar.java的覆蓋率數(shù)據(jù)
默認條件下,UI只與行覆蓋率信息一起注釋;但是,您可以在工作臺偏好中更改它們,并且可以選擇為包、類型以及塊而包含覆蓋率。每一個Java項目的百分比是最后一次執(zhí)行代碼覆蓋率的中斷。您可以在Package Explorer中深入研究各種Java工件(例如,類、類型與方法)以得到較低組合層次上的覆蓋率統(tǒng)計數(shù)據(jù)。
結(jié)果得到的結(jié)果的顏色情況取決于成功率:默認條件下,紅色意味著沒有達到可接受的覆蓋率層次,而綠色則意味著得到了適當?shù)母采w率范圍。一般來說,測試的目的在于達到類可接受覆蓋率層次的結(jié)果。
基于如圖4所示的結(jié)果,第一個測試是不充分的:Car類(以及抽象父類AbstractFourWheelVehicle和Vehicle)并不能達到適當?shù)母采w率層次。幸運的是,您有第二次嘗試的機會:TestCarImproved.java。您可以再一次將測試作為一次正常的JUnit執(zhí)行,而結(jié)果將會在Package Explorer中進行自動更新(圖5)。
圖5.Package Explorer中顯示的TestCarImproved.java的代碼覆蓋率數(shù)據(jù)
Java編輯器
行覆蓋率結(jié)果也是顯示的,并在Java編輯器中有所標記,而您可以使用它來得到一個更加明確的指示,也就是每一類中涉及到了哪一行。在生成覆蓋率數(shù)據(jù)之后,您就可以使用Java編輯器來在項目中打開任意的類了,編輯器中左邊的標尺欄顯示了關(guān)于覆蓋率的信息。圖6顯示了Vehicle.java的結(jié)果:
圖6.Java編輯器中顯示的覆蓋率結(jié)果
顏色編輯與在Package Explorer中所顯示的是一樣的。也就是,默認條件下,綠色的行是覆蓋的而紅色的則不是覆蓋的。在Java編輯器中查看結(jié)果有一個微弱的優(yōu)勢,那就是它還指示了部分覆蓋的行。當在源代碼中有不止一個的可執(zhí)行單元時就會產(chǎn)生部分覆蓋的行,但是它們中只有一個可以被執(zhí)行。例如,查看圖6中setTargetSpeed(int speed)方法中第一行的代碼:第一個可執(zhí)行的單元是if聲明,而第二個可執(zhí)行的單元則是return聲明。默認條件下,一個部分的行會被標上黃色。
#p#
生成報告
您可以將代碼覆蓋率結(jié)果數(shù)據(jù)匯編到報告之中并在Rational Application Developer中查看它們,或者將它們保存到文件系統(tǒng)中以便未來的分析。您可以生成兩種不同類型的報告:Workbench報告(基于Eclipse)與HTML報告。為了生成一份報告,您可以選擇Run>Code Coverage>Generate Report。圖7顯示了報告生成對話框。
圖7.報告生成對話框
您可以在Rational Application Developer中使用對話框中的Quick View選項來創(chuàng)建并查看一個報告,或者使用Save Report選項將其保存到文件系統(tǒng)中去。
工作臺報告
工作臺報告(也叫做基于Eclipse的報告)為項目提供了所有覆蓋率統(tǒng)計數(shù)據(jù)的穩(wěn)固視圖,并包含了執(zhí)行時項目中所有類的覆蓋率數(shù)據(jù)。圖8顯示了一個基于Eclipse流傳的報告。
圖8.一個基于Eclipse報告的覆蓋率結(jié)果
工作臺報告與Rational Application Developer相集成具有額外的優(yōu)勢,因為您可以使用它們作為一個快速的工具,以提供了關(guān)于部分代碼的視角,這些代碼需要改進的測試覆蓋率數(shù)據(jù)。如圖8所示,工作臺報告中的統(tǒng)計數(shù)據(jù)包含了所有層次組成的覆蓋率信息:從一個包到一種方法。右擊任意的Java工件會顯示出一個帶有兩種操作的彈出菜單:在Package Explorer中顯示與在Java編輯器中將其打開。對于識別和研究帶有低覆蓋率的代碼區(qū)域來說,它們是非常有用的工具,因為通過將它們在適當?shù)臑g覽器或者編輯器中打開,從而強調(diào)了代碼的選擇區(qū)域。
#p#
HTML報告
HTML報告顯示了基于Eclipse報告所提供的相同類型的信息,但是呈現(xiàn)的格式卻是HTML的。這些報告能夠發(fā)揮一定程度的作用,因為它們?yōu)樵讵毩⒂赗ational Application Developer之外去分析覆蓋率數(shù)據(jù)提供了一種有效的方法,您可以與團隊的其他成員一起分享,或者將其發(fā)布到一個網(wǎng)站上以方便查看。
在工作臺的外部生成統(tǒng)計數(shù)據(jù)
Rational Code Coverage工具的一個主要特性是其在Rational Application Developer外部生成統(tǒng)計數(shù)據(jù)的能力。它提供了額外的靈活性,并使得您可以定制環(huán)境以利用系統(tǒng)中的Rational Code Coverage特性。例如,一個自然的合并過程就是創(chuàng)建一個構(gòu)建環(huán)境并使用JUnit測試來生成統(tǒng)計數(shù)據(jù)。
通過執(zhí)行以下的三個步驟:評價,執(zhí)行以及生成報告,您可以將Rational Code Coverage特性集成到您的環(huán)境之中。
第1步.評價
您可以使用兩種不同的方法來評價您的程序。第一個就是使用
清單3.本文范例程序的評價Ant任務(wù)的范例用法
- classname="com.ibm.rational.llc.engine.instrumentation.anttask.InstrumentationTask"
- classpath="{path to com.ibm.rational.llc.engine plugin}"/>
- baseLineFile="project.baseline"
- buildPath="VehicleProject"
- outputDir="VehicleProjectInstr"/>
對預(yù)期參數(shù)的快速預(yù)覽,已經(jīng)列在后續(xù)的表2中。
表2.指南任務(wù)的輸入?yún)?shù)
參數(shù)描述
buildPath對文件系統(tǒng)上項目的路徑
outputDir(可選的)評價項目的輸出目錄。如果沒有指定,buildPath中的類將會進行評價。
baseLineFile(可選的)基線項目索引文件的輸出位置。查看接下來的段落以得到關(guān)于該文件更多的信息。
saveBackups(可選的)如果在評價之前先備份原始的類文件,那么您可以設(shè)置為true。
評價的兩種方法都會輸出一個基線文件。所謂的基線文件是一個特定于Rational Code Coverage特性的概念?;€文件包含了項目中所有類的一個索引,并維護了關(guān)于每一個類的額外元數(shù)據(jù)。該文件在報告階段(接下來的第3步)使用以決定程序中的哪一個類不被覆蓋。該步是需要的,因為Rational Code Coverage數(shù)據(jù)收集引擎只是在Java? Virtual Machine(JVM)載入類時才會標記一個類,所以沒有執(zhí)行的類的列表在沒有元數(shù)據(jù)存在的條件下就不能進行決定了。如果基線文件沒有在報告時出現(xiàn),那么沒有載入的類將不會出現(xiàn)在報告中。
第2步.執(zhí)行
為了執(zhí)行評價好的類,您必須在啟動時對Java環(huán)境做適當?shù)呐渲?。?zhí)行過程中所需的兩個特定的參數(shù)解釋如下:
◆-Dcoverage.out.file=
◆向classpath添加
JUnit Ant任務(wù)提供了這些參數(shù)。代碼清單4提供了范例用法。
清單4.怎樣指定Ant啟動中Rational Code Coverage特性論斷的范例
/plugins/com.ibm.rational.llc.engine_ - /RLC.jar file}"/>
#p#
第3步.生成報告
您可以使用Rational Code Coverage特性所提供的另外一項Ant任務(wù)來生成報告。該項任務(wù)使用BIRT Eclipse.org項目所提供的報告功能,并因此需要您去下載BIRT V2.3.2 Reporting Engine獨立版。該操作可以通過訪問http://www.eclipse.org/birt/download,選擇V2.3.2版本并下載Report Engine版本來完成。注意該Ant任務(wù)只能產(chǎn)生HTML報告。
清單5提供了報告Ant任務(wù)的范例用法。注意,作為輸入,它需要在第2步中所生成的覆蓋率數(shù)據(jù)以及在第1步中(可選)所生成的基線文件。
清單5.本文中范例程序報告生成Ant任務(wù)的范例
/plugins/ - com.ibm.rational.llc.common_
.jar plugin}"/> /plugins/ - com.ibm.rational.llc.report_
plugin}"/> /plugins/ - org.eclipse.equinox.common_
.jar plugin}"/> - classname="com.ibm.rational.llc.report.birt.adapters.ant.ReportGenerationTask"
- classpathref="lib.path"/>
- outputDir="{absolute path to the report output directory}"
- coverageDataFile="{absolute path to the coveragedata file generated in step 1}"
- baseLineFiles="{absolute path to the baseline file generated in step 1}"/>
在圖9中顯示有一個范例HTML報告。使用Ant任務(wù)生成HTML報告會提供一種方法,用戶可以通過這種方法來查看獨立于Rational Application Developer之外Ant環(huán)境中生成的統(tǒng)計數(shù)據(jù)。
圖9.HTML報告中的覆蓋率結(jié)果
Ant環(huán)境提供了范例腳本以及構(gòu)建文件,該環(huán)境可以用于指導、執(zhí)行并生成關(guān)于范例程序的報告。如果您對測試該環(huán)境感興趣,那么您可以參考一下Standalone.zip文件中的README文件。
#p#
在WebSphere Application Server上生成統(tǒng)計數(shù)據(jù)
使用WebSphere Application Server來生成代碼覆蓋率統(tǒng)計數(shù)據(jù)在這里是支持的,但是不幸的是,這個版本中并不支持來自Rational Application Developer內(nèi)部的自動化配置。但是,版本中提供的Rational Code Coverage特性足夠靈活以集成到服務(wù)器環(huán)境中去,包括WebSphere Application Server。為了對代碼覆蓋率而配置您的WebSphere Application Server,您需要按照以下步驟進行操作:
1.啟動服務(wù)器
2.登錄到Administrative Console
3.在左邊的窗格中,展開Servers
4.展開Server Types
5.點擊WebSphere程序服務(wù)器
6.選擇適當?shù)某绦蚍?wù)器
7.展開右部窗格選項區(qū)域內(nèi)Server Infrastructure部分中Java and Process Management項
8.點擊Process definition
9.點擊Additional Properties部分中的Java Virtual Machine
10.在 Boot Classpath部分中,添加RLC.jar文件。如上面介紹的那樣,該.jar文件位于Rational Code Coverage數(shù)據(jù)收集引擎中,并位于
11.在Generic JVM arguments中,添加-Dcoverage.out.file={output file} JVM論斷。如上面所述的那樣,該論斷指定了應(yīng)該將輸出的統(tǒng)計數(shù)據(jù)保存在什么地方。
12.保存服務(wù)器配置并重啟服務(wù)器。
圖10顯示了在作出以上所做的變更之后Administrative Console的屏幕截圖。注意在每一個服務(wù)器實例的后面必須有一個指南,這些服務(wù)器實例會執(zhí)行一個代碼覆蓋率程序。
圖10.WebSphere Application Server對Rational Code Coverage特性的配置
在服務(wù)器對代碼覆蓋率進行配置之后,您就可以手動對服務(wù)器進行代碼覆蓋率的配置了(從Administration Console上進行),或者使用Rational Application Developer中的集成支持功能。注意覆蓋率的結(jié)果不會自動導入到Rational Application Developer中以進行分析,這樣您需要執(zhí)行接下來的步驟來將統(tǒng)計數(shù)據(jù)導回到工作區(qū)中:
1.在Rational Application Developer中的Java視角中,右擊Package Explorer并選擇Import
2.展開Code Coverage
3.選擇Code Coverage Data File并點擊Next
4.選擇Data is located on the file system選項并點擊Next
5.在Coverage Data file區(qū)域中,選擇服務(wù)器所提供的文件系統(tǒng)上的覆蓋率數(shù)據(jù)
6.在Into folder區(qū)域中,選擇工作區(qū)中的一個目錄以保存導入的文件。
7.在Associate with Project區(qū)域中選擇適當?shù)捻椖?。您?yīng)該將統(tǒng)計數(shù)據(jù)與工作區(qū)中的項目聯(lián)系起來,工作區(qū)中包含的源代碼用于在服務(wù)器上生成統(tǒng)計數(shù)據(jù)。
8.點擊Finish
當覆蓋率數(shù)據(jù)文件位于工作區(qū)中時,您可以在UI中顯示統(tǒng)計數(shù)據(jù)并生成報告。您可以右擊覆蓋率文件并選擇Code Coverage > Show code coverage indicators或者Generate Report來完成該操作。該功能可以使您更加受益,因為它提供了對分析Rational Application Developer中結(jié)果所用所有工具的訪問途徑。
Paul Klicnik 是位于安大略省馬克姆的 IBM 多倫多實驗室的一名軟件開發(fā)人員。他自從 2008 年以來從事代碼覆蓋工作,從 2006 年從事性能和測試工具領(lǐng)域的工作。Paul 從事過多個 IBM 核心產(chǎn)品的工作,包括 IBM Rational Performance Tester 和 IBM Rational Application Developer,還有 Eclipse 測試和性能工具項目(TPTP)項目。
【編輯推薦】
- slave4j1.0:Eclipse插件的Java代碼生成器發(fā)布
- 10款常用Java測試工具Java測試工具JUnit 4.0 發(fā)布
- Java測試工具JUnit 4.0 發(fā)布
名稱欄目:巧用工具 為Java程序生成代碼做覆蓋統(tǒng)計
當前網(wǎng)址:http://m.fisionsoft.com.cn/article/djhihoi.html


咨詢
建站咨詢
