
状態:
$ mkdir foo && touch foo/.test
$ cp foo/* .
zsh: no matches found: foo/*
(or bash : cp: cannot stat ‘foo/*’: No such file or directory)
隠しフォルダとファイルでいっぱいのディレクトリがあります。何が起こり、解決策は何ですか?
答え1
答え2
免責事項:この回答はBashに固有のものですが、ほとんどはグローバルモードに関する質問に適用されます。
アスタリスク(*
)はワイルドカード文字です。一部の特定の文字セットを置き換え、点(.
)の最初の文字はそのうちの1つではありません。これはUnixファイルシステムがどのように機能するかという特別なケースです。ドットで始まるファイルは「隠された」と見なされます。つまり、などのツールは、明示的に指示しない限り、その項目を「見ない」ことを意味しますcp
。ls
はい
まず、いくつかのサンプルデータを作成しましょう。
$ mkdir .dotdir{1,2} regdir{1,2}
$ touch .dotfile{1,2} regfile{1..3}
今、私たちは以下を持っています:
$ tree -a
.
|-- .dotdir1
|-- .dotdir2
|-- .dotfile1
|-- .dotfile2
|-- regdir1
|-- regdir2
|-- regfile1
|-- regfile2
`-- regfile3
今、いくつかのゲームをしましょう。このコマンドを使用すると、特定のコマンドの特定のワイルドカード()を次のようにecho
リストできます。*
$ echo *
regdir1 regdir2 regfile1 regfile2 regfile3
$ echo reg*
regdir1 regdir2 regfile1 regfile2 regfile3
$ echo .*
. .. .dotdir1 .dotdir2 .dotfile1 .dotfile2
$ echo .* *
. .. .dotdir1 .dotdir2 .dotfile1 .dotfile2 regdir1 regdir2 regfile1 regfile2 regfile3
$ echo .dotdir*
.dotdir1 .dotdir2
行動を変えますか?
このコマンドを使用すると、同様のファイルに加えて一致するようにshopt -s dotglob
動作を変更できます。*
regfile1
.dotfile1
bash
マニュアルページから抜粋
dotglob If set, bash includes filenames beginning with a `.' in the results
of pathname expansion.
例:
$ shopt -s dotglob
$ echo *
.dotdir1 .dotdir2 .dotfile1 .dotfile2 regdir1 regdir2 regfile1 regfile2 regfile3
次のコマンドを使用してこの動作を復元できます。
$ shopt -u dotglob
$ echo *
regdir1 regdir2 regfile1 regfile2 regfile3
あなたの状況は?
あなたの場合は、cp
パターンに一致するすべてのファイルをコピーしたいのですが、*
何もコピーしたくないと言いました。
$ cp foo/.* .
または、フォルダのすべてのコンテンツが必要な場合は、次のことを実行できますfoo
。
$ cp foo .
あるいは、明示的に次のように言うこともできます。
$ cp foot/.* foo/* .
中かっこ拡張を使用するより簡潔な形式bash
:
$ cp foo/{.,}* .
いつでもこのecho
トリックを使用して提案されたファイルモードを表示できます(アスタリスクが属する部分を指す素晴らしい用語です)。
$ echo {.,}*
. .. .dotdir1 .dotdir2 .dotfile1 .dotfile2 abc regdir1 regdir2 regfile1 regfile2 regfile3
ところで、ファイルディレクトリとは異なるディレクトリをコピーするには、通常は再帰的に実行したいと思います。つまり、次に-R
切り替えますcp
。
$ cp -R foo/. .
答え3
シェルは文字を解析するときにこれらのファイルを隠しファイルとして扱うため、*
これらのcp
ファイル名を引数として受け取りません。
明示的に指定してコピーできます。cp foo/.* .
答え4
すべてのファイルとディレクトリをある場所から別の場所にコピーする場合は、標準rsync
コマンドを使用できます。上記の例では、次のようになります。
mkdir foo && touch foo/.test
rsync -a foo/ .
foo
隠しファイルと隠しディレクトリを含むすべてを現在のディレクトリに再帰的にコピーします。末尾のスラッシュはfoo/
rsync にとって重要です。これを使用すると、foo
スラッシュなしでrsyncがコピーする内容のみがコピーされますfoo
。たとえば:-
mkdir src && mkdir dest && touch src/.test
rsync -a src dest // copies 'src' contents to 'dest/src'
rsync -a src/ dest // copies 'src' contents to 'dest'
システム間のコピーを含むrsyncを調整する他の多くのオプションがあります。