文章目錄
- 前言
- 本章節源碼
- 一、什么是javacc
- 二、Mac環境安裝javacc
- 三、javacc測試案例
- 1、編寫詞法描述文件
- 2、借助javacc命令來處理demo01.jj文件
- 3、idea配置輸入參數,運行Adder類方法
- 四、javacc文件編譯類描述
- 4.1、demo1.jj文件生成內容描述&解析轉換過程
- 4.2、解析demo01.jj文件
- 4.3、快速寫一個支持合并字符串的javacc語法文件
- 參考文章
- 資料獲取
前言
博主介紹:?目前全網粉絲4W+,csdn博客專家、Java領域優質創作者,博客之星、阿里云平臺優質作者、專注于Java后端技術領域。
涵蓋技術內容:Java后端、大數據、算法、分布式微服務、中間件、前端、運維等。
博主所有博客文件目錄索引:博客目錄索引(持續更新)
CSDN搜索:長路
視頻平臺:b站-Coder長路
本章節源碼
當前文檔配套相關源碼地址:
- gitee:https://gitee.com/changluJava/demo-exer/tree/master/java-sqlparser/demo-javacc/learn-javacc-demo
- github:https://github.com/changluya/Java-Demos/tree/master/java-sqlparser/demo-javacc/learn-javacc-demo
一、什么是javacc
javacc官網:https://javacc.github.io/javacc/
介紹:JavaCC(Java Compiler Compiler)是一種廣泛使用的解析器和詞法分析器生成工具,主要用于處理編程語言、數據格式以及任何需要精確解析的文本輸入。它最初是為Java語言設計的,但現在也可以用于其他編程環境。JavaCC幫助開發者通過定義語法和詞法規則來創建編譯器前端,包括詞法分析器(Scanner)和語法分析器(Parser),從而簡化了編譯器開發的過程。
簡單來說:JavaCC是一個能生成詞法和語法的分析器的生成程序。
- 詞法分析器,就是對一串文本進行拆分,轉換成一系列的Token。
- 語法分析器,就是對詞法分析器產生的Token,進行校驗。
**應用場景:**JavaCC常被用來開發編譯器、解釋器、特定領域的語言處理器等,也適用于需要對文本進行復雜解析的應用程序中。例如,它可以用來解析SQL查詢、JSON文檔或者自定義配置文件格式。開始使用JavaCC時,你需要編寫一個語法文件(.jj),在這個文件里定義你的語言的語法規則。之后,通過JavaCC工具處理這個文件,即可生成相應的Java代碼,這些代碼實現了你定義的解析邏輯。
二、Mac環境安裝javacc
相關教程:
- windows安裝可見:1.JavaCC安裝與測試
- mac系統安裝可見:https://cloud.tencent.cn/developer/information/%E5%9C%A8%E5%B8%A6%E6%9C%89%E7%BB%88%E7%AB%AF%E7%9A%84mac%E4%B8%8A%E5%AE%89%E8%A3%85javacc-ask
步驟如下:
1)首先提前安裝Homebrew
2)下載和安裝javacc
brew install javacc
查看javacc安裝的目錄:
// 目錄位置:/opt/homebrew/opt/javacc
brew --prefix javacc
3)測試javacc
javacc -version
若是出現異常報錯:
關于version版本范圍表:https://blog.csdn.net/gaofenglxx/article/details/137559852
表示要使用jdk21,jdk21下載地址:https://www.oracle.com/java/technologies/downloads/#jdk21-mac
下載安裝后修改下環境變量JAVA_HOME:
vim ~/.zshrc-- 原始jdk8
export JAVA_HOME="/Library/Java/JavaVirtualMachines/zulu-8.jdk/Contents/Home"
-- 修改為jdk21
export JAVA_HOME="/Library/Java/JavaVirtualMachines/jdk-21.jdk/Contents/Home"source ~/.zshrc
指定jdk21即可,查看當前的javacc版本號。
三、javacc測試案例
1、編寫詞法描述文件
JavaCC的語法描述文件是 擴展名為.jj 的文件,測試所用的語法描述文件內容如下,該描述文件的功能是解析正整數加法運算,并進行計算的解析器的語法描述文件,設置名稱為demo01.jj:
options {STATIC = false;
}PARSER_BEGIN(Adder)
import java.io.*;
public class Adder {public static void main(String[] args) {for (String arg : args) {try {System.out.println(evaluate(arg));
// return(evaluate(arg));} catch (ParseException ex) {System.err.println(ex.getMessage());}}}public static long evaluate(String src) throws ParseException {Reader reader = new StringReader(src);return new Adder(reader).expr();}
}
PARSER_END(Adder)SKIP: { <[" ", "\t", "\r", "\n"]> }
TOKEN: {<INTEGER: (["0"-"9"])+>
}long expr():
{Token x, y;
}
{x=<INTEGER> "+" y=<INTEGER> <EOF>{return Long.parseLong(x.image) + Long.parseLong(y.image);}
}
2、借助javacc命令來處理demo01.jj文件
進入到對應jj文件所在的目錄,執行命令:
javacc demo01.jj
此時就出現了生成的java文件:
3、idea配置輸入參數,運行Adder類方法
我們將生成的代碼移入到java源代碼目錄中:
實際上也可以在采用最原生的方式對目錄中通過執行命令方式去執行我們生成的類:
javac Adder.javajava Adder 1+7
我們這里也可以直接idea工具來配置參數來快速測試,添加參數1+7:
接著我們來運行下該任務:
四、javacc文件編譯類描述
4.1、demo1.jj文件生成內容描述&解析轉換過程
在一開始的javacc的demo案例中通過javacc對demo1.jj文件來進行生成,得到的內容如下:
生成的各個類介紹描述如下:
- XXXXX(指的是Adder):解析類入口
- XXXXXConstants:Token常量,SKIP TOKEN 和TOKEN
- XXXXXTokenManager:詞法分析器
- SimpleCharStream:詞法分析器的輸入流
- Token:Token類
- ParseException:語法解析異常
- TokenMgrError:語法錯誤提示
引用大佬神圖:https://github.com/quxiucheng/apache-calcite-tutorial/blob/a7d63273d0c7585fc65ad250c99a67a201bcb8b5/calcite-tutorial-2-parser/parser-2-javacc-tutorial/README.md
4.2、解析demo01.jj文件
目標:用于解析并計算形如"數字+數字"
的字符串表達式。
選項部分
options {STATIC = false;
}
STATIC = false;
表示生成的解析器類不會是靜態的。這意味著你可以創建該類的對象實例,并可能在多個解析任務之間共享狀態。
解析器定義部分
PARSER_BEGIN(Adder)
// Java 代碼塊
PARSER_END(Adder)
- 這一部分定義了名為
Adder
的解析器。其中包含了主函數main
和evaluate
方法。 evaluate
方法接收一個字符串參數,將其轉換為Reader
對象,并調用expr()
方法來解析并計算表達式的值。
跳過規則
SKIP: { <[" ", "\t", "\r", "\n"]> }
- 定義了哪些字符應被跳過而不進行處理,這里包括空格、制表符、回車符和換行符,它們通常用于分隔輸入中的不同元素。
令牌定義
TOKEN: {<INTEGER: (["0"-"9"])+>
}
- 定義了一個名為
INTEGER
的令牌,它匹配一個或多個連續的數字字符(0-9
)。
解析規則
long expr():
{Token x, y;
}
{x=<INTEGER> "+" y=<INTEGER> <EOF>{return Long.parseLong(x.image) + Long.parseLong(y.image);}
}
expr
方法嘗試匹配一個模式:一個整數后跟一個加號再跟另一個整數,最后是一個文件結束標記(<EOF>
)。- 如果匹配成功,將兩個
Token
對象的image
屬性(即實際匹配到的字符串)轉換為長整型數值,并返回它們的和。
4.3、快速寫一個支持合并字符串的javacc語法文件
options {STATIC = false;
}PARSER_BEGIN(Adder)
import java.io.*;
public class Adder {public static void main(String[] args) {for (String arg : args) {try {System.out.println(evaluate(arg));} catch (ParseException ex) {System.err.println(ex.getMessage());}}}public static String evaluate(String src) throws ParseException {Reader reader = new StringReader(src);return new Adder(reader).concatExpr();}
}
PARSER_END(Adder)SKIP: { <[" ", "\t", "\r", "\n"]> }TOKEN: {<STRING_LITERAL: "\"" (~["\""])* "\""> | // 字符串字面量<IDENTIFIER: (["a"-"z", "A"-"Z"])+> // 標識符或變量名
}String concatExpr():
{Token x, y;
}
{x=<IDENTIFIER> "+" y=<IDENTIFIER> <EOF>{return x.image + y.image;}
}
參考文章
[1]. 1.JavaCC安裝與測試
資料獲取
大家點贊、收藏、關注、評論啦~
精彩專欄推薦訂閱:在下方專欄👇🏻
- 長路-文章目錄匯總(算法、后端Java、前端、運維技術導航):博主所有博客導航索引匯總
- 開源項目Studio-Vue—校園工作室管理系統(含前后臺,SpringBoot+Vue):博主個人獨立項目,包含詳細部署上線視頻,已開源
- 學習與生活-專欄:可以了解博主的學習歷程
- 算法專欄:算法收錄
更多博客與資料可查看👇🏻獲取聯系方式👇🏻,🍅文末獲取開發資源及更多資源博客獲取🍅