web-dev-qa-db-ja.com

「rm *」を実行するときに「一致が見つかりません」を取り除く方法

zshを使用すると、rmに適合しないパターンを選択すると、「一致するものが見つかりませんでした」というメッセージが表示され、出力をリダイレクトする場合でもこのメッセージが表示されます。

# rm * > /dev/zero 2>&1
  zsh: no matches found: *

このメッセージを削除するにはどうすればよいですか?

28
user123456

この動作は、Zshの nomatchオプション によって制御されます。デフォルトでは、コマンドラインに何にも一致しないグロビング式が含まれている場合、Zshは表示されているエラーメッセージを出力し、コマンドをまったく実行しません。これを無効にするには、

setopt +o nomatch

次に、何にも一致しないグロビング式はそのまま残され、rmからエラーメッセージが表示されます(-fを使用して無効にできますが、これは悪い考えです)他の状況では削除したくない場合もあります)。

52
Stephen Kitt

代わりに何をしたいですか? rmをまったく実行しない(1)?他のBourneのようなシェル(2)のように、リテラル_*_引数を指定して実行しますか?まったく引数なしで実行しますか(3)?

  1. files=(*(N)); (($#files)) && rm -- $files。または_(rm -- *) 2> /dev/null_でも、rmによって真のエラーが隠されます。これはばかげています。 _(rm -- * 2>&3 3>&-) 3>&2 2> /dev/null_を使用しても、zshエラーを破棄してrmコマンドのstderrを復元できます
  2. _emulate sh -c 'rm -- *' 2> /dev/null_。次に、shと同様に、zshがその単一のコマンドラインでエミュレートしますが、一致しない_*_はそのままrmおよびrmは、_*_ファイルが存在しないと文句を言います。 rmのstderrをshで行うように抑制して、そのエラーメッセージを抑制しますが、発生したエラーとは対照的に、rmによって真のエラーが隠されるので、それはばかげています。 shの誤動作により、リテラル_*_をrmに渡します。 _rm -f '*'_は存在しない_*_ファイルについて不満を言っていないので、_emulate sh -c 'rm -f -- *'_を実行できます
  3. rm -- *(N)rmは、引数が渡されない場合でも、_rm -f_ではなく、文句を言います:rm -f -- *(N)

一般に、_rm -f_は、すべてのファイルを削除し、rmが返された後もファイルを削除できなかった場合、またはIOWがまだ残っている場合にのみエラーを取得する場合に使用するコマンドです。また、通常、スクリプトで_-f_を使用して、特定の状況でユーザーにプロンプ​​トが表示されないようにする必要があります。

ここで、グロブが一致しないときにrmを呼び出すのは間違っています。 sh1 動作が間違っています。 _*_のようなパターンでは無害ですが、_*.[ch]_のようなパターンでは、一致しないときに_*.[ch]_をそのまま渡すと、_*.[ch]_ファイルが削除される可能性があります間違い:

_$ ls
*.[ch]  foo.txt
$ zsh -c 'rm *.[ch]'
zsh:1: no matches found: *.[ch]
$ ls
*.[ch]  foo.txt
$ sh -c 'rm *.[ch]'
$ ls
foo.txt
_

エラーで失敗するのが最も賢明なことであり、zsh(およびfishcshtcsh、_bash -o failglob_および元のUnix Shell)にはあります。

そして、あなたがその特別なケースに気をつけたいなら、zshは_(N)_グロブ修飾子(noglob)上記(1)の場合と同様です。 fish(少なくとも 最新バージョン では)は、暗黙的なnoglobsetコマンド。したがって、同等のものは次のようになります。

_set files *
if count $files > /dev/null
  rm -f -- $files
end
_

詳細は nullglobがデフォルトではない理由 を参照してください。


1。厳密に言えば、それはBourne Shell(1979年のUnix V7以降)以降のshのみです。以前のバージョンのshglobの名前の由来である引用符で囲まれていないワイルドカードに対して_/etc/glob_を呼び出しました)は動作しましたcshまたは_zsh -o cshnullglob_のように、つまり_/etc/glob_は、どのグロブも一致しない場合にコマンドを中止します(少なくとも1つのグロブが一致しない場合、一致しないグロブを抑制します)一致)。動作は、Bourne Shellによってbrokenでした。

10