我有以下几行:
<INITIAL><<EOF>> {return 0;}
Run Code Online (Sandbox Code Playgroud)
我需要忽略最后一个 EOL -\n或者\r\n在 EOF 之前。我不知道如何将它连接到 EOF 以便它成为一个有效的正则表达式..我试过:
<INITIAL>((\n)|(\r\n))*<<EOF>> {return 0;}
Run Code Online (Sandbox Code Playgroud)
但它说这是一个“无法识别的规则”。
<<EOF>>不是真正的模式符号,因为它不能成为模式的一部分。从逻辑上讲,EOF 标记不是字符;所述<<EOF>>伪图案是可以通过一个空字符串相匹配的唯一弯曲图案。
没有表示输入结束的 flex 模式符号,因此不可能表达“后跟 EOF”的模式。
所以你需要从不同的角度工作:检测一个没有跟随 EOF 的模式。
如果模式后没有 EOF,则必须后跟至少一个字符。我们可以使用尾随上下文运算符编写。一旦我们匹配的模式的那些情况下,该模式的任何剩余的比赛只能如果那场比赛使用的是后面EOF因为最长匹配的,:
\r?\n/(.|\n) { /* A new line NOT followed by EOF */ }
\r?\n { /* A new line followed by EOF */ }
Run Code Online (Sandbox Code Playgroud)
我们需要.|\n在尾随上下文中使用,因为.不匹配\n。由于尾随上下文运算符的优先级,括号是不必要的。
在换行符之后强制检测尾随上下文会使这个扫描器的交互使用变得烦人,因为如果第一个规则返回换行符标记,则在读取另一行之前它实际上不会返回。
顺便说一句,没有必要
<INITIAL><<EOF>> {return 0;}
Run Code Online (Sandbox Code Playgroud)
这是文件末尾的 flex 默认行为,<<EOF>>如果您需要在返回 0 之前执行某些操作,则只需要一个规则。