国产xxxx99真实实拍_久久不雅视频_高清韩国a级特黄毛片_嗯老师别我我受不了了小说

資訊專欄INFORMATION COLUMN

Java代碼分析器(二): 使用DOM API操作抽象語法樹

pf_miles / 1750人閱讀

摘要:請下載一份源代碼,這里有個(gè)對應(yīng)的源碼包元素的組合需要遵守基本的語法規(guī)則不是全部。名字也是表達(dá)式的一種,是指變量名類名包名等元素,它們在中都屬于抽象類,分為和兩種具體類。

另載于 http://www.qingjingjie.com/blogs/3

上篇博客末尾提到了一棵抽象語法樹長什么樣子。JDT提供了一套DOM API來讓我們順利地控制這樣一棵樹。

讀完本篇后請繼續(xù)完成上篇的延伸閱讀:http://help.eclipse.org/ 點(diǎn)擊JDT Plug-in User Guide -> Programmer"s Guide -> JDT Core -> Manipulating Java Code。

各種語法元素用不同的結(jié)點(diǎn)類來表示,一些主要的類有:
CompilationUnit: 編譯單元,相當(dāng)于一個(gè).java文件
AbstractTypeDeclaration: 各種類型的聲明及定義,如類、接口、枚舉、注解。以下幾個(gè)類都繼承自該類
TypeDeclaration: 類或接口
EnumDeclaration: 枚舉類
AnnotationInterfaceDeclaration: 注解,即@interface Xxx {...}
MethodDeclaration: 方法
FieldDeclaration: 域 (成員變量)
Modifier: 修飾符,如public, static, volatile等,也包括注解,如@Override
Block: 代碼塊,也就是花括號(hào){...}所包裹的一段代碼
Statement: 語句,是代碼塊的一部分,也就是以;或}結(jié)尾的一段代碼
Expression: 表達(dá)式,是語句或聲明的一部分, 例如a+b, "seg", a.call(b), ((Number) this)等

其中一些是抽象類,它們會(huì)有一些具體的子類,列舉在抽象類的javadoc中。

結(jié)點(diǎn)之間通過對象引用來連接,舉個(gè)例子,MethodDeclaration主要有這么幾個(gè)屬性:

SimpleName name; //方法名
List parameters; //方法參數(shù)
List modifiers;
List typeParameters; //泛型參數(shù)
Type returnType;
Block body; //方法體
Javadoc javadoc;

為了掌握J(rèn)DT的使用方法,我們需要觀看其javadoc和源代碼,因?yàn)槲臋n太缺乏。這部分源代碼還是挺容易懂的。
請下載一份源代碼,這里有個(gè)Eclipse 4.3.1對應(yīng)的JDT源碼包 http://grepcode.com/snapshot/repository.grepcode.com/java/eclipse.org/4.3.1/org.eclipse.jdt/core/3.9.1

元素的組合需要遵守基本的語法規(guī)則(不是全部)。當(dāng)我們用上篇博客的方式讀入并解析Java代碼時(shí),JDT只會(huì)做詞法分析和語法分析,而不會(huì)做語義分析,因此只能發(fā)現(xiàn)符號(hào)不合法、語句不完整、括號(hào)不匹配之類的簡單錯(cuò)誤,至于變量未聲明、類型不匹配、缺少import、方法未實(shí)現(xiàn)之類的錯(cuò)誤,則不會(huì)發(fā)現(xiàn)。語義分析需要Eclipse workspace的支持,因此需要實(shí)現(xiàn)一個(gè)Eclipse插件,本系列博客不研究這件事;如果費(fèi)點(diǎn)工夫,也是可以自行實(shí)現(xiàn)一定程度的語義分析的,如果有空可以分享一下。

為了更好地理解語法樹結(jié)構(gòu),請讀者運(yùn)行上篇的代碼,解析一個(gè)真實(shí)的.java文件,在debug模式下逐級(jí)展開觀察CompilationUnit的內(nèi)部結(jié)構(gòu)。

然后我們來介紹一些語法概念,方便進(jìn)一步理解:

字面量是表達(dá)式的一種,int, boolean, String的常量(以及null, X.class)在語法上都是字面量(literal)。

名字也是表達(dá)式的一種,是指變量名、類名、包名等元素,它們在JDT中都屬于Name抽象類,分為SimpleName和QualifiedName兩種具體類。SimpleName是不帶"."的標(biāo)識(shí)符,如變量名foo;QualifiedName則是帶有"."的合成名字,如包名java.util.List。QualifiedName是由SimpleName組成的。
根據(jù)Java語法,標(biāo)識(shí)符只能包含字母、數(shù)字、下劃線“_”、美元符號(hào)“$”,且不得以數(shù)字開頭。

從上篇最后的代碼開始,從CompilationUnit出發(fā)跟著對象引用一路走下去,就能分析代碼結(jié)構(gòu)了。但是到了代碼塊一級(jí)就要開始面對數(shù)不清的甚至有嵌套的語句和表達(dá)式了,不得了啊。其實(shí)我們可以使用ASTVisitor來遍歷所有結(jié)點(diǎn),不用自己硬著頭皮一層層去訪問。

像下面的代碼,就自定義了一個(gè)visitor,來遍歷所有的方法調(diào)用,我們把它應(yīng)用到CompilationUnit這棵樹上(也可以應(yīng)用到任意一棵子樹上):

ASTVisitor visitor = new ASTVisitor() {
    @Override
    public boolean visit(MethodInvocation mi) {
        System.out.println(mi);
        return true;
    }
}
compilationUnit.accept(visitor); //應(yīng)用到樹上

這樣它就在這棵樹上走了一圈,碰到合適的結(jié)點(diǎn)就干活。"return true"的作用是告訴visitor繼續(xù)前進(jìn),如果return false,visitor就會(huì)停止前進(jìn)。

再來溜一段復(fù)雜點(diǎn)的代碼,我們把visitor的visit方法改一改:

ASTVisitor visitor = new ASTVisitor() {
    @Override
    public boolean visit(MethodInvocation mi) {
        if (mi.getExpression() instanceof ThisExpression) {
            mi.setExpression(null);
        }
        return true;
    }
}
compilationUnit.accept(visitor);
System.out.println(compilationUnit.toString());

如果代碼中含有this.doThing()這樣的調(diào)用,處理后重新輸出的代碼會(huì)變成doThing(),this被去掉了。

[本篇待續(xù)]

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://specialneedsforspecialkids.com/yun/64142.html

相關(guān)文章

  • Java代碼析器(一): JDT入門

    摘要:另載于這是一個(gè)關(guān)于抽象語法樹的故事。抽象語法樹是對程序代碼的結(jié)構(gòu)化表示,是對代碼進(jìn)行詞法分析語法分析后得到的產(chǎn)物。 另載于 http://www.qingjingjie.com/blogs/2 這是一個(gè)關(guān)于抽象語法樹(Abstract Syntax Tree, AST)的故事。 抽象語法樹是對程序代碼的結(jié)構(gòu)化表示,是對代碼進(jìn)行詞法分析、語法分析后得到的產(chǎn)物。編譯器要用到它,很多生產(chǎn)力工...

    binaryTree 評論0 收藏0
  • 校招社招必備核心前端面試問題與詳細(xì)解答

    摘要:本文總結(jié)了前端老司機(jī)經(jīng)常問題的一些問題并結(jié)合個(gè)人總結(jié)給出了比較詳盡的答案。網(wǎng)易阿里騰訊校招社招必備知識(shí)點(diǎn)。此外還有網(wǎng)絡(luò)線程,定時(shí)器任務(wù)線程,文件系統(tǒng)處理線程等等。線程核心是引擎。主線程和工作線程之間的通知機(jī)制叫做事件循環(huán)。 showImg(https://segmentfault.com/img/bVbu4aB?w=300&h=208); 本文總結(jié)了前端老司機(jī)經(jīng)常問題的一些問題并結(jié)合個(gè)...

    DevTalking 評論0 收藏0
  • 校招社招必備核心前端面試問題與詳細(xì)解答

    摘要:本文總結(jié)了前端老司機(jī)經(jīng)常問題的一些問題并結(jié)合個(gè)人總結(jié)給出了比較詳盡的答案。網(wǎng)易阿里騰訊校招社招必備知識(shí)點(diǎn)。此外還有網(wǎng)絡(luò)線程,定時(shí)器任務(wù)線程,文件系統(tǒng)處理線程等等。線程核心是引擎。主線程和工作線程之間的通知機(jī)制叫做事件循環(huán)。 showImg(https://segmentfault.com/img/bVbu4aB?w=300&h=208); 本文總結(jié)了前端老司機(jī)經(jīng)常問題的一些問題并結(jié)合個(gè)...

    jonh_felix 評論0 收藏0
  • 校招社招必備核心前端面試問題與詳細(xì)解答

    摘要:本文總結(jié)了前端老司機(jī)經(jīng)常問題的一些問題并結(jié)合個(gè)人總結(jié)給出了比較詳盡的答案。網(wǎng)易阿里騰訊校招社招必備知識(shí)點(diǎn)。此外還有網(wǎng)絡(luò)線程,定時(shí)器任務(wù)線程,文件系統(tǒng)處理線程等等。線程核心是引擎。主線程和工作線程之間的通知機(jī)制叫做事件循環(huán)。 showImg(https://segmentfault.com/img/bVbu4aB?w=300&h=208); 本文總結(jié)了前端老司機(jī)經(jīng)常問題的一些問題并結(jié)合個(gè)...

    Rango 評論0 收藏0

發(fā)表評論

0條評論

pf_miles

|高級(jí)講師

TA的文章

閱讀更多
最新活動(dòng)
閱讀需要支付1元查看
<