【问题标题】:PCRE2 - Match every word whose suffix matches a backreferencePCRE2 - 匹配后缀匹配反向引用的每个单词
【发布时间】:2021-04-16 05:20:19
【问题描述】:

给定下面的字符串,

ay bee ceefooh deefoo38 ee 37 ef gee38 aitch 38 eye19 jay38 kay 99 el88 em38 en 29 ou38 38 pee 12 q38 arr 999 esss 555

目标是匹配每个单词,使得后缀是一个与出现在foo 之后的数字相匹配的数字(在这种情况下恰好是 38)。

只有一个子字符串以foo 开头并以数字结尾。预期的匹配都存在于所述子字符串之后。

预期匹配:

gee38
jay38
em38
ou38
q38

我尝试了foo(\d+).*?(\w+\1)\bfoo(\d+).*(\w+\1)\b,但它们无法匹配所有,因为它们要么匹配第一个 (gee38) 要么匹配最后一个 (q38)。

是否有可能只用一个正则表达式匹配所有内容,更重要的是,只需一次运行?

我使用的 PCRE2 引擎的行为方式与 https://regex101.com/r/uFEDOE/1 相同。所以,如果正则表达式可以匹配 regex101 上的多个子字符串,那么我使用的引擎也可以。

【问题讨论】:

  • 您是否总是将“foo”作为具有此后缀的第一个单词?或者是否有实例在以“foo”结尾的单词之前有这个后缀?
  • @Thefourthbird 仅在 foo38 之后。对不起,我误解了你的问题。
  • 这个正则表达式可能会有所帮助:(?:foo|\G(?!^))(\d+).*?(?=(\w+))\w+(?=\1\b)
  • @Michail 太棒了,你可以把它贴出来。我认为如果你在非贪婪匹配之后添加一个单词边界,并在前瞻中使用反向引用,你可以减少步骤数。(?:foo|\G(?!^))(\d+).*?\b(?=(\w+\1))\w+(?=\1)regex101.com/r/T8dmDq/1
  • @第四只鸟您的正则表达式大约快 x2 并且很棒。不幸的是,我不确定像 ab38cd 这样的东西是合法的输出

标签: regex pcre backreference


【解决方案1】:

(?:foo|\G(?!^))(\d+).*?(?=(\w+))\w+(?=\1\b)

Demo

可能是一些尺寸或性能优化。

@Niko Gambt,说一下是否有任何优化对你很重要。

【讨论】:

  • 哇...没想到这是可能的!谢谢!关于优化,它有时会很有用,因为我经常处理大量的序列化数据。
  • 如果你在.*?之后加上\b,性能可以提高大约1.5倍,@Thefourthbird大大建议:(?:foo|\G(?!^))(\d+).*?\b(?=(\w+))\w+(?=\1\b)
  • (?:\G(?!^)|foo)(\d++).*?\b(?=([a-z]++\1))[a-z]++(?=\1) 这改进了一点
  • 是的。也许我们可以用\G(?(?=^).*?foo)替换(?:\G(?!^)|foo)
  • 顺便说一句,你的技术有名字吗?我将其称为“链接”或“迈克尔的链接”:p
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-12-01
  • 1970-01-01
  • 2013-09-06
  • 2020-12-03
相关资源
最近更新 更多