这并不奇怪:
% perl -ne 'print if /c++/' foo
Nested quantifiers in regex; marked by <-- HERE in m/c++ <-- HERE / at -e line 1.
但是,有点:
% grep c++ foo
blah c++ blah
我不知道grep正在做什么来容纳++
- 但我在perl中也是如此。或者,至少,一些优雅的方式来处理这种情况;模式来自用户,他可能会看到grep c++
有效,然后对perl失败感到惊讶。
我不想使用quotemeta
;我的真实代码期望正则表达式模式(来自用户):
while ( my $pattern = shift @pat_list ) {
my $regex = $opts{case} ? qr/$pattern/ : qr/$pattern/i;
my @hits = grep { /$regex/ } @lines;
我想我可以检测到模式有错误然后恢复为quotemeta
。但我似乎无法使用eval
来捕获错误(因为它被视为语法错误?)。
答案 0 :(得分:4)
shell命令grep
至少知道它如何解释正则表达式的三种模式:作为基本RE(默认),作为扩展RE(如果使用-E
或egrep
调用)和Perl兼容的RE(如果使用-P
调用)。对于习惯于Perl的RE引擎的人来说,基本RE的行为有点不同。 grep
的文档说明了您的特定用例:
In basic regular expressions the meta-characters ?, +, {, |, (, and ) lose
their special meaning; instead use the backslashed versions \?, \+, \{, \|, \(,
and \).
这意味着调用grep c++ something.txt
时没有元字符。
请注意,即使是Perl兼容的RE(由着名的库libpcre
提供)也与Perl自己的RE引擎实现的不同。 Perl的引擎功能集在所有RE实现中都非常独特。但是来自libpcre的PCRE(Perl兼容的RE)至少非常相似并且也被广泛使用,例如在PHP,C ++(Boost)中,像grep
这样的工具,和大多数其他编程语言一样。
话虽如此:我建议如果你想在Perl和grep
中使用大多数RE,那么使用grep
的Perl兼容模式,例如: grep --perl-regexp $yourRE $yourFile.txt
。如果您允许任意用户输入,请务必注意shell引用!那是String::ShellQuote。
答案 1 :(得分:1)
如果你想要grep兼容(POSIX)正则表达式,你可以使用POSIX::Regex。 (它不是标准模块,您可能需要使用cpan命令安装它。)
答案 2 :(得分:0)
我的问题的主要观点是错误的。这很好用:
#!/usr/bin/perl -w
use strict;
my $pattern = "c++";
my $regex;
eval { $regex = qr/$pattern/; };
warn "Error detected: $@" if $@;
我已要求删除我的问题。很抱歉浪费了你们所有的时间。
答案 3 :(得分:0)
perl -ne'打印if / c \ + \ + /'foo
在正则表达式中,“+”表示“一个或多个”。