Flex 词法分析器规则,对包含连字符和斜杠的字母数字字符串具有积极的前瞻断言

Flex lexer rule with positive lookahead assertion on alphanumeric strings containing hyphens and slashes

本文关键字:字符串 数字字符 数字 断言 规则 词法分析器 包含 连字符 Flex      更新时间:2023-10-16

我很难为某种类型的令牌构建一个具有积极前瞻性断言的 flex 词法分析器规则,并且可能需要一些帮助。我确定我在这里错过了一些简单的东西。

我要匹配的令牌字符串如下所示:

33-abc-13/12
99-ab-33
o3sehh04/00
glu6-840d/00
vm-22hd
xyz-3

要匹配的令牌对象是一个包含letters and digits的字符串,并且具有slashes and/or hyphens,这种情况很少a dot,可能类似于xx-3006/10.00

不得匹配的(因为其他规则涵盖这些情况)是令牌,例如:

numeric370
hyphen-term
plainterm
00/40

到目前为止,我尝试的是这个规则,并展望未来:

([a-z0-9/-]*)/[-/]+[0-9/-]+

有了上面,我得到的结果接近我想要实现的结果。它匹配上面列出的所有这些字符串,但跳过最后一个字符或数字。匹配的令牌如下所示:

33-abc-13/1
o3sehh04/0
...

不幸的是,该规则也与00/40匹配(导致00/4)。

所以我的问题是我在这里错过了什么?如果可能的话,用一条规则覆盖这些情况会很好,而且速度足够快。我知道词法分析器脚本中处理规则的顺序,因此该规则的位置将是整个集合中的第一个规则之一。 如果不可能,也许打破这一规则将是另一种方式。

在这个项目中,我使用 RE-flex 包 (https://github.com/Genivia/RE-flex),因为它涵盖了 flex 词法分析器接口并提供 unicode(我需要处理wchar_t字符串)。 我的词法分析器是一个带有标记分类的空格标记器,它基本上是在几年前的 flex 2.5 包上构建的。我在令牌处理中重构了一些东西,并转向重新弯曲,因为它给了我更多的机会。分词器输入字符串是简短的简单文本片段,它们的长度不超过 250-300 个字符。到目前为止的背景。

注意:在为词法分析器转换规则之前,我在构建规则时使用 regex101.com 进行检查/实验。它有助于达到正确的方向,但仅此而已。

任何帮助都非常感谢,提前感谢您的努力!

更新:根据 rici 的回答,最终模式现在如下所示:

[a-z0-9/.-]*[/.-][0-9/-]+

这也包括现在包含.的令牌,例如

xx33-4.00
f/44-7.87
...

考虑到我下面评论中的句子分隔符问题只是 模式最后一个字符组中的.。我删除了它,现在它按预期工作。

我对 RE-flex 一无所知(尽管它看起来很酷),但假设它确实与 flex 兼容,同样的方法应该有效:忘记前瞻断言(因为匹配的字符串将不包括前瞻模式,并且您希望匹配整个字符串)并将规则放在所有其他可能匹配相同事物的规则之后

弹性规则为:

  • 比赛时间最长的模式获胜,但
  • 如果两个或多个模式都匹配最长匹配项,则文件中的第一个模式优先。

因此,例如,假设您有以下模式:

[0-9]+("/"[0-9]+)*          { return SLASHED_NUMBERS; }
[a-z0-9/-]*[/-][0-9/-]+     { return GENERAL_TOKEN;   }

[注1]

两者都将匹配00/40,因此,如果这是输入点的令牌,则该令牌将被检测为SLASHED_NUMBERS(文件中的第一个规则)。另一方面,如果您有00/49-23,它将被检测为GENERAL_TOKEN,因为该规则匹配了更多字符。

<小时 />

注释

  1. 我基于您的正则表达式。我不明白"罕见的情况一个点",它似乎没有反映在你的模式中;此外,您的模式似乎比"字母、数字、连字符和斜杠"更具体,但我不确定具体是什么。