有谁知道为什么
grep "p\{2\}" textfile
会在文件中找到“apple”,但
grep p\{2\} textfile
不会?
我是使用命令行和正则表达式的新手,这让我很困惑。
答案 0 :(得分:2)
虽然这已经得到了解答,但由于您对所有这些内容都不熟悉,以下是如何调试它:
- 获取当前shell的pid(使用ps
)。
PID TTY TIME CMD
1611 pts/0 00:00:00 su
1619 pts/0 00:00:00 bash
1763 pts/0 00:00:00 ps
- 从其他shell中,将strace
(系统调用跟踪器)附加到所需的pid(此处为1619):
strace -f -o <output_file> -p 1619
- 运行您尝试过的两个命令
- 打开输出文件并在此处查找所需流程的exec
家庭电话:grep
我机器上的输出有点像:
1723 execve("/bin/grep", ["grep", "--color=auto", "p{2}", "foo"], [/* 19 vars */]) = 0
1725 execve("/bin/grep", ["grep", "--color=auto", "p\\{2\\}", "foo"], [/* 19 vars */]) = 0
现在你可以看到两种情况下grep
的执行方式不同,可以自己解决问题。 :)
仍然是-e旗帜之谜尚未解决......
答案 1 :(得分:1)
如果没有引号,shell将尝试扩展选项。在你的例子中,大括号'{}'在shell中有一个特殊含义,就像星号'*'扩展为通配符一样。
答案 2 :(得分:0)
使用引号,您的完整正则表达式将直接传递给grep。如果没有引号,grep会将您的正则表达式视为p{2}
。
编辑:
为了澄清,在正则表达式传递给grep之前,如果没有引号,shell会删除斜杠。
尝试:
echo grep p\{2\} test.txt
你会看到你的输出......
grep p{2} test.txt
引号阻止shell在转到grep之前转义字符。你也可以逃避斜线,它可以不用引号 - grep p\\{2\\} test.txt
答案 3 :(得分:0)
来自grep手册页
In basic regular expressions the meta-characters ?, +, {, |, (, and ) lose their special meaning; instead use the backslashed versions \?, \+, \{, \|, \(, and \).
所以这两个功能等同于
egrep p{2}
和
grep "p\{2\}"
第一个使用ERE(扩展正则表达式),第二个使用BRE(基本正则表达式),因为你使用grep(当你不使用-e开关时支持BRE)并且你用引号括起来所以“\ {”作为一个特殊的BRE角色扩展。
您的第二个实例无法正常工作,因为您只需查找文件中不存在的文字字符串2 {p}
你可以通过尝试来证明grep正在将你的字符串扩展为BRE:
grep "p\{2"
grep会抱怨
grep: Unmatched \{
答案 4 :(得分:0)
第一个使用正则表达式,然后pp
:
echo "apple" | grep 'p\{2\}'
第二个按字面意思模糊图案,然后是p{2}
:
echo "ap{2}le" | grep p\{2\}