ディレクトリとそのサブディレクトリ内のすべてのファイルの最初の50行を検索する必要があります。
これは再帰的な部分を実行しますが、各ファイルの最初の50行だけに制限するにはどうすればよいですか?
grep -r "matching string here" .
これらのファイルのいくつかは巨大であり、最初の50行でのみ一致させたいと思います。一部のファイルでメガバイトのバイナリデータを検索しないことで、プロセスを高速化しようとしています。
一致するファイルだけが必要な場合:
find . -type f -exec bash -c 'grep -q "matching string here" < <(head -n 50 "$1")' _ {} \; -printf '%p\n'
または
find . -type f -exec bash -c 'grep -q "matching string here" < <(head -n 50 "$1") && printf '%s\n' "$1"' _ {} \;
一致する文字列のみが必要な場合:
find . -type f -exec head -n 50 {} \; | grep "matching string here"
または、より良い、
find . -type f -exec head -q -n 50 {} + | grep "matching string here"
そして、両方が必要な場合:
find . -type f -exec bash -c 'mapfile -t a < <(head -n 50 "$1" | grep "matching string here"); printf "$1: %s\n" "${a[@]}"' _ {} \;
備考
sed
--head
の代わりにgrep
を使用すると少し簡単になります。-exec ... +
を使用できますが、その場合は、内部ループを自分でコーディングする必要があります。 (読者に残された些細な演習)。膨大な数のファイルがある場合、これは非常にわずかに効率的かもしれません。オリジナルのようにgrep出力が必要な場合は、次のようにすることができます。
find . -type f | while read f; do
if head -n 50 "$f"|grep -s "matching string here"; then
grep "matching string here" "$f" /dev/null
fi
done
ファイル名のみが必要な場合は、2番目のgrepをecho "$f"
に置き換えることができます。
目的の機能を得るには、いくつかの異なるユーティリティを組み合わせる必要があります。 find
コマンドを使用してディレクトリを再帰し、すべてのファイルを検索し、見つかった各ファイルに対してhead
コマンドを実行します。 head
コマンドを使用して、各ファイルの最初の50行のみをダンプできます。最後に、出力をgrepにパイプして、目的の文字列を検索します。
find . -type f -exec head -n 50 {} ";" | grep "matching string here"