検索ツリーから特定のディレクトリを除外したいと思います。.aaa
現在のディレクトリの隠しサブディレクトリです。その名前にaaa_rc_bbb, xxx_rc_xxx
含まれるより多くのサブディレクトリを除外したいと思います。rc
しかし、それは無視せずにrc
サブディレクトリを含む結果を提供します。*rc*
ワイルドカードが機能しないようです。
find -L /students/projects/myname/ -name .aaa -prune -o -path */*/class_project/*/*/pikachu/*/*/*rc*/ -prune -o -path */*/class_project/*/*/pikachu/*/*/bambi/bambi.txt | head -n50 | xargs ls
。
また、次のルートでのみ検索したいと思います。*/*/class_project/*/*/pikachu/*/*/bambi/bambi.txt
助けてください。私は何が間違っていましたか?
ベストアンサー1
最初の問題は、引用されていないglob()があることです*
。これらのパスはすべて単一引用符で囲む必要があります(例:)'*/*/class_project/*/*/pikachu/*/*/bambi/bambi.txt'
。これにより、シェルがワイルドカード文字を渡す前に拡張するのを防ぎますfind
。
-prune
次に、基本検索サブ式の前に表示するサブ式が必要です。ちなみに、すべての名前を次の複合式にまとめることができます-prune
。
find \( \( -name '*foo*' -o -name '*bar*' \) -a -prune \) -o \( -name baz -a -print \)
これは、その名前を含む、または含むbaz
ファイル/ディレクトリを除いて、指定されたファイルを探したいことを意味します。foo
bar
いくつかの注意:
- 私は(AND)演算子とかっこについてはかなり自由なので、
-a
あいまいさはありません。 - 括弧の目的は、優先順位を変更し、他のほとんどの式タイプと同様に、エスケープされて
\
渡される前にシェルで解釈されないようにすることですfind
。 - 私は2つの
-name
テストを使用していますが、他のテスト(例-path
:)は最初の入れ子括弧内にあるかもしれません。テストに一致するファイル/ディレクトリは切り捨てられ、次のテスト(最後の括弧セット)には適用されません。 -print
作業を部分から区別するために明示的にすることをお勧めします-prune
。
明確にするために、より一般的な表現スタイルで書き直しましょう。
((name=='*foo*' OR name=='*bar*') AND prune) OR (name==bar AND print)
でも
if (name=='*foo*' OR name=='*bar*')
prune
else if (name==bar)
print
fi
一般的な優先順位ルールとデフォルトのブール演算子が与えられたら、-a
次のように単純化できます。
find \( -name '*foo*' -o -name '*bar*' \) -prune -o -name baz -print
find
コマンドを実行すると、見つかったファイルに対して作成されたパスが/
文字で終わらないため、-path '*/*/class_project/*/*/pikachu/*/*/*rc*/'
一致できません。ファイルの種類を制限するには、その末尾を削除し、/
可能であれば追加する必要があります。-type d
目次。
また、*/*
パターンマッチングに含まれるすべての文字列にはが/
含まれていますfoo/bar/baz
。ここで、パスはすべてinで始まるので、inはすでにそこにあることが/students/projects/myname/
わかっているので重複します。/
*/*
/
あなたの意図を正しく読んだ場合は、2番目のサブ式のテストを実行しません。つまり、ファイルが切り捨てられない場合は印刷しようとします。それで、これは次のように続きます。
find -L /students/projects/myname/ \
\( \
-name .aaa \
-o -path '*/class_project/*/*/pikachu/*/*/*rc*' \
-o -path '*/class_project/*/*/pikachu/*/*/bambi/bambi.txt' \
\) -prune \
-o -print