Antlr4学习记录(二)

antlr4操作使用

一:操作环境
环境:java8+maven+idea
antlr4:使用idea搜索然后下载插件

*二:定义.g4文件,编写语法定义文件。
关键字:
grammar
grammar是规则文件的头,需要与文件名保持一致。当antlr生成词法语法解析的规则代码时,类名就是根据grammar的名字来的。

rule
rule是antlr生成词法语法解析的基础。包括了lexer与parser,每条规则都是key:value的形式,以分号结尾。lexer首字母大写,lexer小写。

示例:

grammar Dsl;    //定义规则文件grammar
@header {        //一种action,定义生成的词法语法解析文件的头,当使用java的时候,生成的类需要包名,可以在这里统一定义
 package antlr;
 }

//parsers
sta:(sql ender)*;  //定义sta规则,里面包含了*(0个以上)个 sql ender组合规则
ender:';';  //定义ender规则,是一个分号
sql   //定义sql规则,sql规则有两条分支:select/load
    : SELECT ~(';')* as tableName   //select语法规则,以lexer SELECT开头, 以as tableName 结尾,其中as 和tableName分别是两个parser
    | LOAD format '.' path  as tableName //load语法规则,大致就是 load json.'path' as table1,load语法里面含有format,path, as,tableName四种规则
    ;    //sql规则结束符
as: AS;   //定义as规则,其内容指向AS这个lexer
tableName: identifier;  //tableName 规则,指向identifier规则
format: identifier;   //format规则,也指向identifier规则
path: quotedIdentifier; //path,指向quotedIdentifier 
identifier: IDENTIFIER | quotedIdentifier;  //identifier,指向lexer IDENTIFIER  或者parser quotedIdentifier
quotedIdentifier: BACKQUOTED_IDENTIFIER;  //quotedIdentifier,指向lexer BACKQUOTED_IDENTIFIER

//lexers antlr将某个句子进行分词的时候,分词单元就是如下的lexer
//keywords  定义一些关键字的lexer,忽略大小写
AS: [Aa][Ss];
LOAD: [Ll][Oo][Aa][Dd];
SELECT: [Ss][Ee][Ll][Ee][Cc][Tt];

//base  定义一些基础的lexer,
fragment DIGIT:[0-9];   //匹配数字
fragment LETTER:[a-zA-Z];  //匹配字母
STRING        //匹配带引号的文本
    : '\'' ( ~('\''|'\\') | ('\\' .) )* '\''
    | '"' ( ~('"'|'\\') | ('\\' .) )* '"'
    ;
IDENTIFIER    //匹配只含有数字字母和下划线的文本
    : (LETTER | DIGIT | '_')+
    ;
BACKQUOTED_IDENTIFIER   //匹配被``包裹的文本
    : '`' ( ~'`' | '``' )* '`'
    ;

//--hiden  定义需要隐藏的文本,指向channel(HIDDEN)就会隐藏。这里的channel可以自定义,到时在后台获取不同的channel的数据进行不同的处理
SIMPLE_COMMENT: '--' ~[\r\n]* '\r'? '\n'? -> channel(HIDDEN);   //忽略行注释
BRACKETED_EMPTY_COMMENT: '/**/' -> channel(HIDDEN);  //忽略多行注释
BRACKETED_COMMENT : '/*' ~[+] .*? '*/' -> channel(HIDDEN) ;  //忽略多行注释
WS: [ \r\n\t]+ -> channel(HIDDEN);  //忽略空白符

// 匹配其他的不能使用上面的lexer进行分词的文本
UNRECOGNIZED: 

三:通过插件生成代码
在这里插入图片描述

四:后段使用
1:添加Maven依赖

<dependency>
     <groupId>org.antlr</groupId>
     <artifactId>antlr4-runtime</artifactId>
     <version>4.7.1</version>
</dependency>```

2:遍历解析树

    public static void main(String[] args) throws IOException {
        String sql= "Select 'abc' as a, `hahah` as c  From a aS table;";
        ANTLRInputStream input = new ANTLRInputStream(sql);  //将输入转成antlr的input流
        DslLexer lexer = new DslLexer(input);  //词法分析
        CommonTokenStream tokens = new CommonTokenStream(lexer);  //转成token流
        DslParser parser = new DslParser(tokens); // 语法分析
        DslParser.StaContext tree = parser.sta();  //获取某一个规则树,这里获取的是最外层的规则,也可以通过sql()获取sql规则树......
        System.out.println(tree.toStringTree(parser)); //打印规则数
    }

原文地址:https://www.jianshu.com/p/21f2afca65e8

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值