web-dev-qa-db-ja.com

Linuxで100万のイメージを1つのディレクトリから別のディレクトリに移動する最も速い方法は何ですか?

1つのローカルディレクトリから別のローカルディレクトリに移動する必要がある30GBのディスク容量を占める100万のイメージがあります。

これを行う最も効率的な方法は何でしょうか? mvcprsync?他に何か?

私はこれらを取る必要があります:

/path/to/old-img-dir/*
                     00000000.jpg
                     --------.jpg  ## nearly 1M of them! ##
                     ZZZZZZZZ.jpg

ここに移動します:

/path/to/new/img/dir/
14
Ryan

rsyncは、ローカルシステムとリモートシステムの両方に対応する多くのクライアント/サーバーバックグラウンド処理を実行するため、不適切な選択です。

mvがおそらく最良の選択です。可能であれば、mv directory_old directory_new のではなく mv directory_old/* directory_new/。このようにして、100万個ではなく1個のものを移動します。

26
Richard
find src_image_dir/ -type f -name '*.jpg' -print0 | xargs -0r mv -t dst_image_dir/ 
  • これは引数の展開をオーバーフローしません。
  • 必要に応じて、ファイル拡張子を指定できます。 (-名前 ...)
  • find -print0xargs -0を使用すると、名前にスペースを使用できます。
  • xargs -rは、移動するものがなければ、mvを実行しません。 (mvは、ソースファイルが指定されていない場合に文句を言います)。
  • 構文mv -tを使用すると、最初に宛先を指定し、次にxargsで必要なソースファイルを指定できます。
  • ディレクトリ全体の移動は、ディレクトリに含まれるファイルの数に関係なく一定の時間で行われるため、もちろんはるかに高速ですが、
    • 少しの間、ソースディレクトリが消え、問題が発生する可能性があります。
    • プロセスが現在のディレクトリを出力ディレクトリとして使用している場合(常に移動していない場所からのフルパスを参照するのとは対照的)、再起動する必要があります。 (ログローテーションで行うように)。

ちなみに、本当に大量のファイルを一度に移動する必要があるのか​​と自問します。バッチ処理は過大評価されています。出来上がった瞬間に処理できるのであれば、膨大な量の作業を積み重ねないようにしています。

2つのディレクトリが同じファイルシステムにある場合は、ディレクトリの内容ではなく、ディレクトリでmvを使用します。

2つの異なるファイルシステムに存在する場合は、rsyncを使用します。

rsync -av /source/directory/ /destination

ソースの末尾の/に注意してください。つまり、ディレクトリ自体ではなく、ディレクトリのコンテンツをコピーします。 /をオフのままにしても、ファイルはコピーされますが、/destination/directoryという名前のディレクトリに置かれます。 /を使用すると、ファイルは/destinationに配置されます

rsyncは、rootとして実行した場合、またはファイルの所有者である場合に、ファイルの所有権を維持します。また、個々のファイルのmtimeも保持します。

7
UtahJarhead
tar cf - dir1 | (cd dir2; tar xf -)

tar cf - dir1 | ssh remote_Host "( cd /path/to/dir2; tar xf - )"

'cp'を使用すると、各ファイルはopen-read-close-open-write-closeを実行します。 Tarは、読み取りと書き込みに複数のプロセスを使用し、同時に複数のファイルを操作する複数のトレッドを使用します。シングルCPUボックスでも、マルチスレッドアプリの方が高速です。

2
maholt

Directory_oldとdirectory_newの両方が同じファイルシステム上にあるため、mvの代わりにcp -lをオプションとして使用できます。 cp -lは、元のファイルへのハードリンクを作成します。 「移動」が完了し、結果に満足したら、これらのファイルをdirectory_oldから削除できます。速度の点では、最初にリンクを作成してから元のリンクを削除するため、「mv」と同じになります。しかし、このアプローチでは、これが理にかなっている場合、最初から始めることができます

1
Serge

空き容量がある場合は、それらを単一の.tarファイルにアーカイブし(圧縮なしの方が高速です)、そのファイルを移動してアーカイブ解除します。

0
endolith

それは依存します(tm)。ファイルシステムがコピーオンライトの場合、コピー(cpまたはrsyncなど)はムーブに相当します。ただし、最も一般的なケースでは、移動(mv)が最も高速です。これは、ファイルが配置されている場所を示すデータの断片を単純に切り替えることができるためです(注:これは過度に単純化されています)。

したがって、平均的なLinuxインストールでは、mvを使用します。

編集: @FrédéricHamidiのコメントには良い点があります。これは、両方が同じファイルシステムとディスク上にある場合にのみ有効です。それ以外の場合、データはとにかくコピーされます。

0
carlpett

宛先の性質により、このタスクを実行する最も効率的な方法が決まります。ローカルシステムを使用しているとしましょう。PWDは現在/です。 /aには数百万の画像が含まれています。私たちの仕事は、すべてのサブディレクトリ構造を維持しながら、すべての画像を/bに移動することです。また、/aおよび/bが、それぞれローカルに接続されたディスク上の2つの異なるパーティションのマウントポイントであると仮定します。ターピペでこのタスクを実行したいと思います。これには時間がかかる場合があるため、screentmuxを使用しているか、バックグラウンドプロセスとして実行していることを確認してください。

tar -C /a -cf . | tar -C /b -xf -

これにより、/aのすべてのファイルとディレクトリが/bにコピーされるため、エラーなしで完了したことを確認したら、/aをクリーンアップする必要があります。

0
J. M. Becker

少なくとも〜10kのファイル(ディレクトリなし)をコピーするために、cpは次のように不平を言いました:

/ bin/cpを実行できません:引数リストが長すぎます

最適なオプションはRsyncです。

rsyncソースターゲット

そして、それは非常に迅速に行われました!

0
Nico