PCRE
– (Perl兼容的正则表达式)文档中阅读,并且正式表达了一些有趣的技巧。当我继续阅读和耗尽自己时,我停止了因为使用一些(* …)模式的一些混乱。
我的问题和困惑与(* PRUNE)和(* FAIL)有关
现在参考(* SKIP)的行为就像(* PRUNE)一样,除了如果模式是无保护的,那么颠簸的提前不是下一个字符,而是在遇到的(* SKIP)主题的位置。
文档指出(* PRUNE)会导致匹配失败,如果该模式的其余部分不匹配的主题当前起始位置。它表示(* FAIL)与(?!)否定断言同义。在模式中的给定位置强制匹配失败。
所以基本上(* FAIL)的行为就像一个失败的负面断言,是(?!)的同义词
和(* PRUNE)导致匹配失败在主题的当前起始位置,如果有一个后来的匹配失败导致回溯达到它。
How are these different when it comes to a point of failing?
Can anyone provide examples of how these are implemented and used correctly?
所有测试都是通过全局搜索(使用preg_match_all()函数进行的)。
(*失败)
baabo caaco daado caac(*FAIL)|aa.|caaco|co [0] => aab [1] => caaco [2] => aad
(* FAIL)导致与模式中的“坏字符”完全相同的行为。如果用“R”替换,您将获得完全相同的结果:caacR | aa。| caaco | co。为了更通用,你可以通过一个“总是失败的子模式”替换(* FAIL),如:(?!),(?= a(?<!a))... a(第一个来自“baabo”):没有惊喜,第二个选择找到第一个结果。 (aab) c(第一):正则表达式引擎遇到第一个“c”并尝试第一个替代方法,并找到:caac,但子模式被强制失败。那么正则表达式引擎(总是从第一个“c”)尝试失败的第二个替代方案,第三个选项成功。 (caaco) a(第一个来自“daado”):第二个结果是第二个替代。 (aad) (*跳跃)
baabo caaco daado caa(*SKIP)c(*FAIL)|aa.|caaco|co [0] => aab [1] => co [2] => aad
该动词定义了一个点,超过此点,当子模式稍后失败时,不允许正则表达式引擎回溯。结果,所有在子模式下发现的所有字符都被一次全部消耗,不能用于模式的另一部分(替代)。
a(第一个来自“baabo”):第二个选择找到第一个结果。 (aab)
c(第一):正则表达式引擎在第一种情况下找到caac,然后失败((FAIL)动词的原因),回溯到第二个“c”,但不允许回溯到先前匹配的字符(“ caa“)之前的(* SKIP)动词。
c(第二):现在,正则表达式引擎总是尝试第一个替代方案,但在这个新的位置,失败,因为有一个“o”而不是“a”之后,它回溯到第二个“c”。请注意,在这种情况下,这些字符不像以前那样被消耗,因为子模式之前已经到达(* SKIP)动词。
第二个选项被测试并失败(不以“c”开头)。第三个选择也失败了,因为下一个字符是“o”而不是“a”。
第四种替代方案成功并获得第二种结果。 (共)
a(第一个来自“daado”):第三个结果是第二个替代。 (aad)
(*修剪)
baabo caaco daado caa(*PRUNE)c(*FAIL)|aa.|caaco|co [0] => aab [1] => aac [2] => aad
这个动词不同于(* SKIP),因为它不禁止使用所有以前匹配的字符,但如果子模式稍后会失败,则跳过第一个匹配的字符由子模式(或禁止一个子模式开始)。
a(第一个来自“baabo”):第二个选择找到第一个结果。 (aab)
c(第一):正则表达式引擎在第一种情况下找到caac,然后失败,但是现在从第一个“c”跳回第一个“a”,因为第一个“c”被跳过。
a(第一个来自“caaco”):第一个选择被尝试和失败,第二个成功并给出第二个结果。 (aac)
a(第一个来自“daado”):第三个结果是第二个替代。 (aad)