正则表达式匹配线与管道的n倍

时间:2018-06-11 09:43:09

标签: regex grep

我使用grep来匹配具有正好52个管道(|)的行。我使用的grep命令是:

grep -nP "^(.*?\|){52}"

-P因为懒惰修饰符?不起作用。运行此操作时,将显示以下消息:PCRE's backtracking limit is exceeded。我想这里的perl-like regex有问题。

  • 我的内存耗尽了吗?
  • 我正在使用正则表达式中的问题吗?
  • 我可以使用更好的正则表达式吗?

非常感谢!

1 个答案:

答案 0 :(得分:2)

您的PCRE模式(仅匹配任何0+字符的52次出现,尽可能少,最多并包括|字符,并且不检查除此之外的任何文本)包含重复捕获组,当引擎匹配,它还将每个|| char之前的每个0+字符放入一个组中,然后在每次迭代时重写该值。在某些实现中,它会导致您提供的错误。

请注意,此任务不需要PCRE正则表达式,因为要匹配任何字符,但|可以使用[^|],然后使用仅仅POSIX ERE模式(启用-E选项)grep

grep -En "^([^|]*\|){52}[^|]*$"

注意最后添加的[^|]*$。它匹配除|以外的任何0+字符,然后断言行尾位置。因此,只匹配包含53个| - 分隔字段的行。

否则,您可能会考虑使用awk解决方案(如PS建议的那样):

awk -F'|' '{if (NF==53) {print NR ":" $0;}}'

我们检查53个| - 分隔的字段并打印行号:和行本身。