ANTLR4:隐式或显式标记定义
ANTLR4: implicit or explicit token definition
在 ANTLR4 中使用显式标记定义有哪些优点和缺点?我发现单括号中的文本比创建单独的标记并使用它代替文本更具描述性和更易于使用。
例如:
grammar SimpleTest;
top: library | module ;
library: 'library' library_name ';' ;
library_name: IDENTIFIER;
module: MODULE module_name ';' ;
module_name: IDENTIFIER;
MODULE: 'module' ;
IDENTIFIER: [a-zA-Z0-9]+;
生成的令牌是:
T__0=1
T__1=2
MODULE=3
IDENTIFIER=4
'library'=1
';'=2
'module'=3
如果我对 'library'
"token" 不感兴趣,因为规则已经确定了我要匹配的内容,无论如何我都会跳过它,替换它是否有意义它带有 LIBRARY
和令牌声明? (然后令牌的数量会增加。)为什么这是 ANTLRWorks 中的警告?
Antlr(和大多数 compiler/compiler 生成器)实现使用单独的词法分析器和解析器的概念,主要是出于性能原因。在这个模型中,词法分析器负责读取输入字符串中的实际字符,并以更简洁的形式返回找到的标记列表,例如每个标记的枚举或 int 代码。解析器将处理这些标记而不是原始输入,以便于实施和提高性能。
有两种方式"declare"在Antlr中使用token,一种是显式的,有一个规则的模式表达式,另一种是隐式的,总是一个固定的字符串。
ExplicitRegExp: [A-Z][a-z]+; // lexer rule starts with uppercase letter
ExplicitFixed: 'fixed';
parserRule: 'implicit' ExplicitRegExp; // parser rules starts with lowercase letter
显式声明令牌时,会为其分配一个 int 代码以用于解析状态机。假设 ExplicitRegExp
变为 1,ExplicitFixed
变为 2。但是解析器还需要 implicit
标记才能正确解析语法,因此分配了 implicit
标记代码 3 隐含地.
怎么那么糟糕?您可能在语法的不同部分有错别字:
a : 'implicit' c;
b : 'implcit' d; // typo here
并且你的语法不会按预期工作,因为 implcit
将是一个有效的标记,分配了 int-code 4。由于 Antlr auto- 这也使得你的 grammar/lexer 更难调试为隐式规则生成名称,如 T___0
。另一件事是你失去了词法分析器规则的顺序,可能会有所不同(通常不是因为隐式标记都是固定内容)。
Antlr 编译器可以选择给你一条错误信息并要求你显式地写标记,但它选择放手,只是警告你不要那样做,可能是为了 prototyping/testing原因。
为了让 Antlr 开心,请以详细的方式进行并声明所有令牌:
grammar SimpleTest;
top: library | module ;
library: 'library' library_name=IDENTIFIER ';' ; // I'm using aliasing instead of different parser rule here, just a preference
module: 'module' module_name=IDENTIFIER ';' ;
MODULE: 'module' ;
LIBRARY: 'library' ;
IDENTIFIER: [a-zA-Z0-9]+;
然后,如果您通过其显式名称(如 MODULE
)或通过其内容(如 'module'
)引用固定标记,则没有任何区别。
实际上,隐式标记和显式标记之间存在差异:
来自 "The Definitive ANTLR4 Reference",第 76 页:
ANTLR collects and separates all of the string literals and lexer
rules from the parser rules. Literals such as 'enum' become lexical
rules and go immediately after the parser rules but before the
explicit lexical rules.
ANTLR lexers resolve ambiguities between
lexical rules by favoring the rule specified first.
我的亮点。
在 ANTLR4 中使用显式标记定义有哪些优点和缺点?我发现单括号中的文本比创建单独的标记并使用它代替文本更具描述性和更易于使用。
例如:
grammar SimpleTest;
top: library | module ;
library: 'library' library_name ';' ;
library_name: IDENTIFIER;
module: MODULE module_name ';' ;
module_name: IDENTIFIER;
MODULE: 'module' ;
IDENTIFIER: [a-zA-Z0-9]+;
生成的令牌是:
T__0=1
T__1=2
MODULE=3
IDENTIFIER=4
'library'=1
';'=2
'module'=3
如果我对 'library'
"token" 不感兴趣,因为规则已经确定了我要匹配的内容,无论如何我都会跳过它,替换它是否有意义它带有 LIBRARY
和令牌声明? (然后令牌的数量会增加。)为什么这是 ANTLRWorks 中的警告?
Antlr(和大多数 compiler/compiler 生成器)实现使用单独的词法分析器和解析器的概念,主要是出于性能原因。在这个模型中,词法分析器负责读取输入字符串中的实际字符,并以更简洁的形式返回找到的标记列表,例如每个标记的枚举或 int 代码。解析器将处理这些标记而不是原始输入,以便于实施和提高性能。
有两种方式"declare"在Antlr中使用token,一种是显式的,有一个规则的模式表达式,另一种是隐式的,总是一个固定的字符串。
ExplicitRegExp: [A-Z][a-z]+; // lexer rule starts with uppercase letter
ExplicitFixed: 'fixed';
parserRule: 'implicit' ExplicitRegExp; // parser rules starts with lowercase letter
显式声明令牌时,会为其分配一个 int 代码以用于解析状态机。假设 ExplicitRegExp
变为 1,ExplicitFixed
变为 2。但是解析器还需要 implicit
标记才能正确解析语法,因此分配了 implicit
标记代码 3 隐含地.
怎么那么糟糕?您可能在语法的不同部分有错别字:
a : 'implicit' c;
b : 'implcit' d; // typo here
并且你的语法不会按预期工作,因为 implcit
将是一个有效的标记,分配了 int-code 4。由于 Antlr auto- 这也使得你的 grammar/lexer 更难调试为隐式规则生成名称,如 T___0
。另一件事是你失去了词法分析器规则的顺序,可能会有所不同(通常不是因为隐式标记都是固定内容)。
Antlr 编译器可以选择给你一条错误信息并要求你显式地写标记,但它选择放手,只是警告你不要那样做,可能是为了 prototyping/testing原因。
为了让 Antlr 开心,请以详细的方式进行并声明所有令牌:
grammar SimpleTest;
top: library | module ;
library: 'library' library_name=IDENTIFIER ';' ; // I'm using aliasing instead of different parser rule here, just a preference
module: 'module' module_name=IDENTIFIER ';' ;
MODULE: 'module' ;
LIBRARY: 'library' ;
IDENTIFIER: [a-zA-Z0-9]+;
然后,如果您通过其显式名称(如 MODULE
)或通过其内容(如 'module'
)引用固定标记,则没有任何区别。
实际上,隐式标记和显式标记之间存在差异:
来自 "The Definitive ANTLR4 Reference",第 76 页:
ANTLR collects and separates all of the string literals and lexer rules from the parser rules. Literals such as 'enum' become lexical rules and go immediately after the parser rules but before the explicit lexical rules.
ANTLR lexers resolve ambiguities between lexical rules by favoring the rule specified first.
我的亮点。