有時候想在代碼中執行某個關鍵詞,會用下面的語句:
find . -type f -name "*.java" | xargs grep -n "<keyword>"
大部分情況下良好,但也有出問題的時候,比如某個目錄中含有空格。那么檢索這個目錄下所有的文件都會報錯。為此,需要改一下腳本,將路徑放到引號中。
find . -type f -name "*.java" | xargs -I {} grep -n "<keyword>" "{}"
這樣又出現了新的問題:結果中都沒有命中文件的文件名了。只有行號和命中行的內容。像下面這樣:
:123 public class xxxxxx...
沒錯,我用的是 cygwin. 上面的命令在 linux 下是沒有問題的。但在 cygwin 下不行。即使在find中加上 -print 也無濟於事。
不過,用另一個參數可以解決這個問題,即 print0,腳本如下:
find . -type f -name "*.java" -print0 | xargs -0 grep -n "<keyword>"
xargs -0 大意是讓輸入項以 \0 作為分隔,而不是以空白符號。-print0 和 -0 配合使用。帶空格的路徑再不會被當作多個輸入項了。
接下來考慮完善這個命令,如果想同時檢索以 .java, .xml, .jsp 等結束的文件。該怎么辦叫做?
find . -type f -name "*.java" -print0 -o -name "*.xml" -print0 -o -name "*.jsp" -print0 | xargs -0 grep -n "<keyword>"
然后在 .bashrc 中給這個命令起個別名:
alias grepj='find . -type f -name "*.java" -print0 -o -name "*.xml" -print0 -o -name "*.jsp" -print0 | xargs -0 grep -n'
命名就簡化成 grepj keyword,這樣就完美了。
注意每一個檢索條件后都要跟一個 -print0 參數。