すべてのサブディレクトリでファイルを再帰的に検索する2つの方法のうち、どちらがより速くより良いですか?
find . -regex ".*/.*abc.*"
または
find . | grep ".*abc.*"
答え1
UNIXファイル名は通常、0x00(NULL)および0x2F(/)を除いてオクテット(8ビットバイト)で構成できます。他のすべてのオクテットは有効です。これには、0x0A(改行文字)などの良い内容が含まれます。
あなたのfind
例は、奇妙な文字(改行文字など)を含むファイル名を正しく処理します。
find | grep
このような状況に直面すると、あなたの例は奇妙で間違った結果を提供します。一つ「Line 1\nLine 2」というファイルは次のとおりです。二つ文書)。
使用できますfind -print0 | grep -z
(たとえば、LinuxでGNUバージョンを使用している場合)。これにより精度が維持されます。より多くのメモリを使用します。オプションを使用して、findに拡張正規表現(例:)を使用するように指示できます-regextype
。
非常に複雑なマッチングを実行したい場合は、コマンドラインを短いPerlプログラムに変換して編集して複雑さを追加できるスクリプトが好きfind2perl
です。find
答え2
find . -regex ".*/.*abc.*"
すべてのデータをfind . | grep ".*abc.*"
生成します。ファイル名にスペースが含まれているまれな場合でも機能するため、より安定しています。find
grep
find . -regex ".*/.*abc.*"
どちらのコマンドもフルパスインクルードを探しますabc
。これには、名前を含むファイルだけでなく、abc
名前を含むディレクトリに含まれるファイルも含まれますabc
。名前に含まれるファイルのみを検索するには、abc
次のようにします。
find -name '*abc*'
ksh、bash、またはzshでは、echo **/*abc*
代わりに以下を実行できます。**/
すべてのサブディレクトリを再帰的に表示します。 kshでは、最初にset -o globstar
実行(に入れる必要があります)する必要があります~/.kshrc
。 Bashでは、まずshopt -s globstar
実行(に入れる必要があります)する必要があります~/.bashrc
。
答え3
パターンマッチングを使用している場合は、追加の述語またはfind
アクションを追加できます。
# look only for matching directories
find . -regex ".*/.*abc.*" -type d
# run a command on each match
find . -regex ".*/.*abc.*" -exec echo 'I found a file named {}' ';'
find
プロセスを作成したりパイプを実行したりする必要はないので、検索のみを実行する方が速いかもしれませんが、気付くことができるかどうかgrep
は疑問です。