その単語を含むすべてのファイルfoo
とその単語を含むファイルを見つけるには、bar
次のようにします。
grep -Ilri foo . | xargs grep -i bar
(大文字と小文字を区別せずにバイナリファイルを除外します。)... ただし、ファイルパスが次の場合
/Users/myusername/Text Files
それではうまくいきません。だから今xargs
部品
grep -i bar /Users/myusername/Text Files
しかし実際にはそうする必要がある
grep -i bar "/Users/myusername/Text Files"
または
grep -i bar /Users/myusername/Text\ Files
どのように機能させるのですか? (macOS Montereyから)。
答え1
grep
ヌルバイトでファイル名を区切るGNUの-Z
/オプションをサポートし--null
(FreeBSDは長い--null
バリエーションのみをサポート)、ヌルバイトをxargs
入力区切り文字として使用するオプション-0
(一部あり)をサポートする場合は、それを使用してファイル名を--null
安全に処理するできます。
grep -Ilri --null foo . | xargs -0 grep -i bar
grep
そして、これらのxargs
非標準オプションをサポートしていない場合(ただし、どちらも標準ではない-r
)、-I
次のものを使用できますfind
。
find . -type f -exec grep -Iiq foo {} \; -exec grep -iq bar {} \; -print
現在のディレクトリから始まるファイルを探し、見つかったファイルごとにgrep
「foo」が含まれているかどうかを確認するgrep
ために実行されます。その名前。
これは非常に効率的ではありませんが、安全に機能します。
答え2
foo
UnixシステムでPOSIXツールを強制的に「該当する単語とその中の単語を含むすべてのファイルを検索する」(テストされていません):bar
find . -type f -exec \
awk '
FNR==1 { x=y=0 }
{ $0 = tolower($0) }
/foo/ { x=1 }
/bar/ { y=1 }
x && y { hits[FILENAME]; nextfile }
END { for (fname in hits) print fname }
' {} +
または必要に応じて:
find . -type f -exec \
awk '
FNR==1 { x=y=0 }
{ $0 = tolower($0) }
/foo/ { x=1 }
/bar/ { y=1 }
x && y && !seen[FILENAME]++ { print FILENAME; nextfile }
' {} +
上記のいずれの場合も、効率性のためにこれをサポートするawkを使用しますがnextfile
、サポートしていないawkでも同じファイル名を複数回印刷しないようにコードを記述します。
上記は、部分文字列や正規表現と文字列の一致に興味がないと仮定しています。