繁体   English   中英

jFlex中的正则表达式,带有硬编码的异常

[英]Regex in jFlex with hardcoded exceptions

我需要在jFlex中使用一个正则表达式来匹配包含一些字符的字符串文字,然后是一个连字符,再加上一个单词。 但是,有一些硬编码的例外。 我的jFlex版本是1.6.1

我的正则表达式是:

SUFFIXES = labeled|deficient
ALPHANUMERIC = [:letter:]|[:digit:]
AVOID_SUFFIXES = {SUFFIXES} | !({ALPHANUMERIC}+)
WORD = ({ALPHANUMERIC}+([\-\/\.]!{AVOID_SUFFIXES})*)

字符串"MXs12-labeled"应标记为'MXs12', '-', 'labeled' (以后由不同的正则表达式捕获的连字符),而"MXs12-C123"'MXs12-C123'因为C123不在后缀列表中。

但是,我获得的令牌是"MXs12-labele" - "MXs12-labele"外禁止的字母短一个字母。

一个明显的解决方案是在正则表达式中包含其他非{ALPHANUMERIC}字符,但这也会将该字符添加到匹配项中。

另一个解决方案似乎是使用负前瞻,但是每次我尝试解析它们时它们都返回语法错误-jFlex似乎不支持它。 Flex似乎不支持regex超前断言(快速lex分析器)

有人知道如何在jFlex中解决此问题吗?

如您所见,使用正匹配比使用负匹配要容易得多。 (显然, labelelabeled不匹配,而且它是labeled的最长前缀,与labeled不匹配,因此逻辑上是,如果尝试匹配!labeled的单词, labele作为匹配项。

JFlex不会实现否定的超前断言,该断言虽然稍有不同,但仍然存在问题。 负前向断言肯定会拒绝后缀MXs12-labeled ,但它也将拒绝在后缀MXs12-labeledblack ,这将是一个有点出人意料,我想。

但是,如果您用积极的比赛改写它,那真的很简单。 这个想法是指定每次正面比赛需要做什么。 在这种情况下,我们会想用的正赛做-labeled是把它放回输入流,这是可以做到的yypushback 这将建议规则如下:

{ALPHANUMERIC}+ ({DELIMITER}{ALPHANUMERIC}+)* "-labeled"  { yypushback(8); /* return the WORD */ }
{ALPHANUMERIC}+ ({DELIMITER}{ALPHANUMERIC}+)* "-deficient"  { yypushback(10); return /* return the WORD */ }
{ALPHANUMERIC}+ ({DELIMITER}{ALPHANUMERIC}+)* { return /* return the WORD */ }

请注意,顺序很重要,因为该序列依赖于优先级高于最后一个模式的前两个模式。 (与前两个模式之一匹配的输入也将与最后一个模式匹配,但是按指示顺序的规则,最后一个模式将不会获胜。)

那可能不是您真正想要的。 它将处理您的问题中指示的MXs12-labeledMXs12-C123 MXs12-labeledblack MXs12-labeled-blackMXs12-labeled-black都将作为单个令牌进行报告; 我不清楚您对这些投入的期望是什么。

Rici的答案解决了这个问题yypushback()正是我所需要的。 截至目前

  1. jflex捕获带或不带后缀的所有字符串
  2. yypushback()的输出部分中还有其他Java正则表达式,检查字符串是否有后缀,如果有则使用yypushback()

通过使用其他Java正则表达式,我可以涵盖上述的MXs12-labeled-black情况,例如"\\\\-labeled$"确保后缀位于传递的字符串的末尾,并且MXs12-labeled-black将作为一个令牌返回,而MXs12-labeled为三个令牌。 。 非常感谢你!

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM