有誰知道爲什麼問題有關shell命令和grep
grep "p\{2\}" textfile
會發現 「蘋果」,如果它在文件中,但
grep p\{2\} textfile
不會呢?
我是使用命令行和正則表達式的新手,這讓我很困惑。
有誰知道爲什麼問題有關shell命令和grep
grep "p\{2\}" textfile
會發現 「蘋果」,如果它在文件中,但
grep p\{2\} textfile
不會呢?
我是使用命令行和正則表達式的新手,這讓我很困惑。
使用引號,您的完整正則表達式直接傳遞給grep。如果沒有引號,grep會將您的正則表達式視爲p{2}
。
編輯:
爲了澄清,不帶引號的斜線正在殼去除之前,你的正則表達式被傳遞到grep。
嘗試:
echo grep p\{2\} test.txt
,你會看到你的輸出...
grep p{2} test.txt
引號防止外殼逃逸字符他們得到給grep之前。你也可以逃避你的斜線,它會工作沒有引號 - grep p\\{2\\} test.txt
如果沒有-e選項,grep不支持regex。我已經嘗試了很多方法,並且不知道爲什麼它以單向方式工作而不是其他方式 – nsfyn55 2011-05-06 19:27:30
grep s {2} pom.xml不返回任何內容,但grep「s \ {2 \}」pom.xml返回所有單詞組件的實例。 grep s \ {2 \}也不會返回 – nsfyn55 2011-05-06 19:29:48
等等,什麼? '-e'對於以'-'開頭的模式是一種方便(並且早於'--'約定)。 'grep'支持POSIX BREs(並且,作爲GNU擴展,ERE語法反斜槓);在POSIX BREs中定義'{}'需要反斜槓(但不在ERE中,這是GNU獲得其擴展的想法)。 – geekosaur 2011-05-06 19:41:18
沒有引號,shell將嘗試擴展選項。在你的情況下,大括號'{}'在shell中具有特殊含義,就像星號'*'擴展爲通配符。
雖然這已經回答了,但因爲你是新來這一切的東西,這裏是如何調試它:
- 獲得當前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
- 從其他外殼,附着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旗神祕尚未解決....
從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\}"
第一用途ERES(擴展正則表達式),第二個使用BREs裏面(基本正則表達式)在你的例子中,因爲你使用grep(當你支持BRE時不要使用-e開關),並且用引號括起來,所以「\ {」會被擴展爲一個特殊的BRE字符。
您二審不工作,因爲你只是在尋找文本字符串2 {P}不以你的文件存在
可以證明的grep通過嘗試擴大你的字符串作爲BRE:
grep "p\{2"
的grep會抱怨
grep: Unmatched \{
第一種使用正則表達式裏grep圖案,然後pp
:
echo "apple" | grep 'p\{2\}'
第二個字面上的裏grep模式,然後p{2}
:
echo "ap{2}le" | grep p\{2\}
我認爲你做了一個更有趣的發現貼在下面的答案。 grep不應該支持你在沒有-e開關的情況下進行輸入,但是如果你用引號括起來的話,grep應該不會支持。我會繼續尋找,但會有興趣看到答案是什麼。 – nsfyn55 2011-05-06 19:32:10
@ nsfyn55:grep完美支持zjmiller輸入的內容。在上述情況下,如果未指定'e'選項,則默認使用'G'選項。它與'grep -G「p \ {2 \}」textfile'相同。 – 2011-05-06 20:05:47
@empo是我現在明白了。請參閱下面的答案。 – nsfyn55 2011-05-10 15:47:27