grepコマンドに2つの*を使用すると、何も返されない理由を知っている人はいますか?私の元のコマンドは次のとおりです。
find | grep 0000\:00\:*.0/usb1/authorized_default
この例では、PCIフォルダ名がわからないファイルを返そうとします。このコマンドは期待どおり(*ワイルドカード)完全に機能し、usb1が「1a」フォルダにあることを確認します。
"usb1"を "usb *"に置き換えるために別のワイルドカードをコマンドに入れた場合、grepが結果を返さないのはなぜですか?私の究極の目標は、すべてのauthorized_defaultファイルを返すことです。これは他の方法でより効率的に実行できることを知っています。私の質問はこれを行う方法ではありませんが、方程式に別の「*」記号を入れたときにgrepが結果を返さないのはなぜですか?
find | grep 0000\:00\:*.0/usb*/authorized_default
お時間と回答ありがとうございます。
答え1
正規表現は、0000:00:*.0/usb1/authorized_default
文字列0000:00
+ 0個以上のコロン+すべての文字+と一致します0/usb1/authorized_default
。
*
合計を置き換えると、次を含むすべての.
文字列と一致します。 (ランダムな文字()の後にランダムな数字()が続くものと一致します。)0000:00
0/usb1/authorized_default
.*
*
.
同様に、etc。とusb*/
一致しますが、一致しません。us/
usb/
usbbb/
usb1
実際には、*
パラメータで引用されていない部分がgrep
グローバル文字として扱われるという問題もあります。シェルを通して、grep
見る前に。したがって、globパターンで一致できるファイルがある場合は、0000\:00\:*.0/usb*/authorized_default
goに影響を与えますgrep
。複数の一致は複数の引数とみなされ、grep
最初の一致以降の引数はファイル名と見なされます。
これが発生しないようにするには、コマンドラインで正規表現の前後に引用符を入れます。
とにかくgrep
@Kusalanandaが言ったように、ここには必要さえありません。オプションを使用して、ファイル名をグローバルパターンと一致させる-name
ことができます。find
少なくとも一部の実装では、ファイル名を正規表現に一致させるオプションfind
もあります。-regex
正規表現にはさまざまなバリエーションがあります。以下を参照してください。私の正規表現がXでは動作しますが、Yでは動作しないのはなぜですか?
答え2
ilkkachuがすでに指摘したように、デフォルトの正規grep
表現を使用すると、これは:*
0個以上一致し:
、b*
0個以上一致することを意味しますb
。
grep
を出力する代わりにをfind
使用してfind
ファイルを見つけます。通常、ファイル名には改行文字が含まれており、grepが機能しない可能性があります。また、表示したいパス名を直接フィルタリングする方がfind
効率的で安全です。
find . -type f -name 'authorized_default'
パス名の他の部分を一致させる必要がある場合:
find . -type f -path '*0000:00:*.0/usb*/authorized_default'
-path
ファイル名はワイルドカードパターンのように機能します-name
が、パス名のファイル名部分だけではなくフルパスと一致します(aは*
1つ以上のものと一致します/
)。
関連: