web-dev-qa-db-ja.com

cpコマンドを使用して複数のファイルをコピーする場合、コピーするときにファイルの名前を変更できますか?

これが本当か偽か疑問に思っていました。

3
Ice

cpは、単一のファイルを別のファイル名にコピーできます(つまり、宛先を「名前変更」)ことができますが、複数のファイルに別のファイル名を指定する方法はありません。したがって、答えはノーです。複数のファイルをコピーする場合、cpは名前を変更できません。

cpに3つ以上の引数を指定すると、すべてのファイルが最後の引数(ディレクトリ)にコピーされます。例えば_cp file1 file2 file3 /path/to/destdir/_

GNU cpを使用すると、ソースファイルの前に宛先を指定できる_-t_または_--target-directory_オプションがあります。例:_cp -t /path/to/destdir/ file1 file2 file3_

_-t_は、_... | xargs cp -t destdir/_や_find ... -exec cp -t destdir/ {} +_などと一緒に使用すると特に便利です。

他のいくつかのGNUツール(mvおよびlnを含む)も同じ_-t_または_--target-directory_オプションを持っています。


コピーするときに複数のファイルの名前を変更する場合、最も簡単な方法は、それを実行するスクリプトを作成することです。

スクリプトの大部分を自動的に生成できます。これを行うには多くの方法がありますが、ここでは最も簡単な方法の1つを使用します(例として_*.txt_に一致するファイル名を使用)。

_find . -maxdepth 1 -name '*.txt' \
   -exec echo cp \'{}\' \'/path/to/dest/newfile\' \; > mycp.sh
_

(ここでは、水平スクロールバーを避けるために、fileコマンドを2行に分割していますが、これはすべて1行に入力できます)

これにより、次のような出力が生成されます。

_$ ls -1 *.txt
dict.txt
qstat.txt
x.txt
foo'bar.txt

$ find . . -maxdepth 1 -name '*.txt' \
  -exec echo cp \'{}\' \'/path/to/dest/newfile\' \;
cp './qstat.txt' '/path/to/dest/newfile'
cp './x.txt' '/path/to/dest/newfile'
cp './dict.txt' '/path/to/dest/newfile'
cp './foo'bar.txt' '/path/to/dest/newfile'
_

次に、お好みのテキストエディタで_mycp.sh_を編集し、各newfileコマンドラインのcpを、コピーしたファイルの名前を変更する名前に変更します。一部のファイルの名前を変更したくない場合は、宛先からnewfileを削除し、宛先のみをパスとして残します。

_'./foo'bar.txt'_をソースファイル名として使用した出力の最後の行に注意してください。ファイル名には_'_文字が含まれているため、この行は埋め込まれた_'_を_'\''_なので、行は次のようになります。

_cp './foo'\''bar.txt' '/path/to/dest/newfile'
_

または、GNU sed(NULで区切られた行の_-z_または_--null-data_オプションを使用))およびxargs自動的にそれを行うことができます:

_find . -maxdepth 1 -name '*.txt' -print0 | 
    sed -z -e "s/'/'\\\''/g" | 
    xargs -0 -r -i echo cp \'{}\' \'/path/to/dest/newfile\' > mycp.sh
_

スクリプトの編集が終了したら、_sh mycp.sh_を使用してスクリプトを実行できます。

11
cas

いいえ、cpはコピーするファイルの名前を変更しません。各ファイルをターゲットディレクトリの同じベース名のファイルにコピーします。 cpがファイル名を変更する唯一のケースは、単一のファイルをコピーし、ターゲットとしてディレクトリではなくフルネームを指定する場合です。

cpの一部のバージョンでは、既存のターゲットファイルがある場合、その名前を変更できます。

コピーされているファイルの名前を変更する場合は、 pax を使用できます。これは、ディレクトリツリーをコピーしたり、アーカイブを作成または解凍するためのユーティリティです。これはPOSIXシステムでは必須のユーティリティですが、一部のLinuxディストリビューションではデフォルトでインストールされません(ただし、パッケージとして提供されています)。 paxを使用すると、sedスタイルのs/REGEX/REPLACEMENT/命令を適用してファイルの名前を変更できます。

pax -rw -pe -s/2015/2016/ source/ target/

source/foo-2014.txtsource/2015.txtなどのファイルをそれぞれtarget/foo-2014.txtおよびtarget/foo-2016.txtにコピーします。