pcre regexp-奇怪的Lookbehind断言不是固定宽度

pcre regexp-奇怪的Lookbehind断言不是固定宽度,regex,pcre,Regex,Pcre,我对regexps有些陌生,我正在努力理解这个regexp: (?<!mix\s|mixe[rds]\s|mixing\s)with(?:out)? 但我得到了以下错误: Lookbehind断言不是固定宽度 我理解lookback是如何工作的(它返回固定宽度,然后尝试匹配),但是lookback中的两个regexp不是同一个regexp吗 (我在这里找到了一些信息,但我仍然不清楚为什么在这种情况下它不起作用) 在这种情况下它不起作用,因为子模式包含一个量词?。当找到这个量词时,正则

我对regexps有些陌生,我正在努力理解这个regexp:

(?<!mix\s|mixe[rds]\s|mixing\s)with(?:out)?
但我得到了以下错误:

  • Lookbehind断言不是固定宽度
我理解lookback是如何工作的(它返回固定宽度,然后尝试匹配),但是lookback中的两个regexp不是同一个regexp吗

(我在这里找到了一些信息,但我仍然不清楚为什么在这种情况下它不起作用)

在这种情况下它不起作用,因为子模式包含一个量词
。当找到这个量词时,正则表达式引擎决定您的子模式不再具有固定长度(这是真的)

即使这两个子模式是等价的(但regex引擎忽略了这一点),但存在量词的事实也会导致模式分析失败

另一方面,pcre接受由管道分隔的若干固定长度的子模式

避免pcre出现此问题的经典解决方法包括使用
\K
功能放弃以前从匹配结果中找到的字符:

(?<!mix)(?:e[rnds]|ing)?\s\Kwith(?:out)?

(?似乎引擎需要一个补丁。如果我有一个
*
+
使得无法预先确定长度,我会理解,但是a?表示有没有,所以子模式可以分解以找到宽度并使用它。我真的对这些信息感兴趣,因为我认为在我的下一个项目中,我希望o创建一个regexp生成器。你给出了你想要包含和排除的单词,它给出了一个优化的regexp@Fabrizio:允许使用
或其他量词完全相同,因为在这种情况下,您可以将任意数量的
(并最终嵌套)放入子模式中。“自动生成优化的正则表达式”:你在做梦吗?@Fabrizio:也许使用回溯控制动词是一个不错的选择,特别是组合
(*SKIP)(*FAIL)
,或者如果你使用捕获组来选择你想要的分支和要丢弃的分支(这两种方法的主要思想是使用你想要避免的字符)从未听说过这样的事情。你会如何在这个场景中应用它?@Fabrizio:看看这篇帖子:
(?<!mix)(?:e[rnds]|ing)?\s\Kwith(?:out)?