我正在尝试使用可选的捕获组来构建python正则表达式。我的正则表达式适用于大多数情况,但无法将其中的匹配项放在其中一个测试用例中。

我要匹配并捕获以下情况:


命名空间::工具名称:: 1.0.1
命名空间:: tool_name
工具名称:: 1.0.1
工具名称


这是我到目前为止拥有的正则表达式:

(?:(?P<namespace>^[^:]+)::)?(?P<name>[^:]*)(?:::(?P<version>[0-9\.]+))?


这个正则表达式适用于我所有的4个测试用例,但是我遇到的问题是情况3,在名称空间组中捕获了tool_name,在名称组中捕获了1.0.1。我希望它们分别被正确的组,名称和版本捕获

谢谢

最佳答案

您可以通过用*替换+(看起来总是存在)来使tool_name regex部分成为强制性的(看起来总是存在),并限制此模式以匹配三个以负号分隔的点分隔数字位:

^(?:(?P<namespace>[^:]+)::)?(?!\d+(?:\.\d+){2})(?P<name>[^:]+)(?:::(?P<version>\d+(?:\.\d+){2}))?


请参见regex demo

细节


^-字符串开始
(?:(?P<namespace>[^:]+)::)?-可选的非捕获组,将除:以外的任意1个以上的字符匹配到“命名空间”组中,然后仅匹配::
(?!\d+(?:\.\d+){2})-负前瞻,不允许digits.digits.digits模式出现在当前位置之后
(?P<name>[^:]+)-组“名称”::以外的任何1个或多个字符
(?:::(?P<version>\d+(?:\.\d+){2}))?-匹配::的可选非捕获组,然后组“版本”捕获1个以上的数字以及2个重复的.和1个以上的数字。

关于python - 正则表达式将匹配项存储在错误的捕获组中,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/54952803/

10-16 11:28