好,所以我有一个正则表达式,可用来解析单引号/双引号内的所有文本,大多数情况下它工作正常,但是如果给定的文本足够大,它将尝试分配20KB但失败了
<b>Fatal error</b>: Out of memory (allocated 1686110208) (tried to allocate 20480 bytes)
这是导致此错误的结果代码行。
preg_match_all('/([\'"])(?:(?!\1|\\\\).|\\\\.)*\1/', $content, $output_array, PREG_OFFSET_CAPTURE);
如果“ $ content”是某个大小,则会发生错误
问题之一是(?:a|b)*
部分,它一个接一个地占用字符并消耗内存。它也无法快速失败。要改善模式,您必须像这样展开此部分:a*(?:ba*)*
,并限制回溯位置的记录,您可以放置所有格修饰符:a*+ (?:ba*)*+
。
为了有效,模式是:
$p = '~" [^"\\\\]*+ (?s:\\\\. [^"\\\\]*)*+ " | \' [^\'\\\\]*+ (?s:\\\\. [^\'\\\\]*)*+ \'~xS';
如果使用php> = 7.2,则可以在最后删除S修饰符。
注意:捕获引用并使用反向引用是一个错误的主意。