特定の検索で検索アクションが機能しない

特定の検索で検索アクションが機能しない

find特定のファイル セットのサイズを一覧表示するコマンドを使用しようとしていますが、出力が得られません。使用するコマンドは次のとおりです。

find POD -type f -name *.mp3 -or -name *.ogg -ls

出力は生成されません。一方:

find POD -type f -name *.mp3 -or -name *.ogg

出力が生成されるので、次のアクションも試しました:

-printf "%p %k KB\n"
-exec ls -ls '{}' \;
-print0

しかし、これらすべては出力を生成しません。これらのアクションのいずれかを別の式で使用すると、例:

find . -maxdepth 1 -type f -printf "%p %k KB\n"

期待通りの出力が得られました。何が問題なのか分かる人はいますか? 実行しているのは:

Linux irimi 3.10.37-1-MANJARO #1 SMP Mon Apr 14 20:56:29 UTC 2014 x86_64 GNU/Linux

別名、最新の Manjaro Linux ディストリビューション。私が使用するシェルは/bin/bashバージョンです4.3.8(1)-release

SHELLOPTS私の環境変数の内容は次のとおりです。

braceexpand:emacs:hashall:histexpand:history:interactive-comments:monitor

私のBASHOPTS環境変数は次のとおりです:

cdspell:checkwinsize:cmdhist:complete_fullquote:dotglob:expand_aliases:extglob:extquote:force_fignore:histappend:hostcomplete:interactive_comments:nocaseglob:progcomp:promptvars:sourcepath

繰り返しになりますが、これをデバッグするためのご協力をいただければ幸いです。

答え1

罠があるおよび/またはfind.のキーワードは、orアクション (-lsこの例では ) を含む、後続のすべてのパラメーターに適用されます。のない(または が付属している)and式は、読み取り順に評価され、最終停止は false になります。 はありません。orandimplicit ()

つまり、その命令はfind POD -type f -name *.mp3 -or -name *.ogg -ls

  • ファイルの検索(PODディレクトリから開始) --- ファイルが見つからない場合:STOP
  • そうでない場合 (ファイルが見つかった場合) パターン マッチングをチェックします*.mp3 --- パターンが一致する場合 : STOP ! (ORここから適用され、前のコマンドが失敗した場合にのみ適用されます (ただし、前のコマンドのみであり、前のコマンド グループは失敗しません))

また、コマンド ラインに実行ステートメント ( -ls、、-exec.... -print) を追加すると、暗黙のコマンドはなくなり、-print1) のすべての条件が true (ファイルとパターンが一致) の場合は何も実行されません。最後のものを削除すると、各条件分岐の最後に-ls暗黙の分散が存在します。-print

  • パターンが一致しない場合は、パターンに一致するもの (ファイル/ディレクトリ) を検索し*.ogg、それらを一覧表示します (これは-ls条件コマンドではなく、前のコマンド/テストの「パターン」が true の場合にのみ実行されます*.ogg)。ただし、1) のため、2) は mp3 ファイル以外のファイルに対してのみ評価されます。ファイルがない場合、.ogg何も表示されません。

解決策1 各論理分岐で実行コマンドを繰り返す

   find POD -type f -name "*.mp3" -ls -or -name "*.ogg" -ls

解決策2(シェルで保護された)括弧を追加

   find POD -type f \( -name "*.mp3" -ls -or -name "*.ogg" \) -ls

注記 現在のディレクトリでシェルパターンの評価を回避するには、パターンを保護する必要があります。

答え2

評価順序(明示的な優先順位がない)が原因だと思います。例えば、

-name '*.mp3' -o -name '*.ogg' -ls

-name '*.ogg'が偽と評価された場合、lsアクションは実行されません。括弧を使用してOR式をグループ化することで、期待どおりの動作を得ることができます。たとえば、

$ ls tests
file1.mp3  file2.mp3  file3.mp3

それから

$ find tests \( -name '*.mp3' -o -name '*.ogg' \) -print
tests/file3.mp3
tests/file1.mp3
tests/file2.mp3

一方

$ find tests -name '*.mp3' -o -name '*.ogg' -print

出力は生成されません。

$ find tests -name '*.mp3' -o -name '*.ogg'

は暗黙的に次のように扱われるため、特別なケースである。

$ find tests \( -name '*.mp3' -o -name '*.ogg' \) -print

findまた、シェルがそれらを展開しないように、コマンド内のシェル グロブを引用符で囲むかエスケープするのが良い方法であることにも注意してください。findNON-BUGSのマニュアルページのセクションを参照してください。

関連情報