Kami memiliki masalah dengan folder menjadi berat dengan ratusan ribu file kecil.
Ada begitu banyak file yang melakukan rm -rf
pengembalian kesalahan dan sebaliknya yang perlu kita lakukan adalah sesuatu seperti:
find /path/to/folder -name "filenamestart*" -type f -exec rm -f {} \;
Ini berfungsi tetapi sangat lambat dan terus-menerus gagal kehabisan memori.
Apakah ada cara yang lebih baik untuk melakukan ini? Idealnya saya ingin menghapus seluruh direktori tanpa mempedulikan konten di dalamnya.
linux
command-line
files
rm
Toby
sumber
sumber
rm -rf *
dalam folder mungkin gagal karena terlalu banyak argumen; tetapi bagaimanarm -rf folder/
jika Anda ingin menghapus seluruh direktori?rm -rf
?fsck
di atasnya untuk merebut kembali blok-blok disk yang tidak digunakan, tetapi pendekatan itu tampaknya berisiko dan mungkin tidak lebih cepat. Selain itu, pemeriksaan sistem file mungkin melibatkan melintasi pohon sistem file secara rekursif.ccache
pohon file yang sangat besar, danrm
butuh waktu lama (dan membuat seluruh sistem lamban), itu jauh lebih cepat untuk menyalin semua file lain dari sistem file, memformat, dan menyalinnya kembali. Sejak saat itu saya memberikan pohon file besar kecil seperti sistem file khusus mereka sendiri, sehingga Anda dapatmkfs
langsung, bukanrm
.Jawaban:
Menggunakan rsync sangat cepat dan sederhana.
Jawaban @ sarath menyebutkan pilihan cepat lain: Perl! Tolok ukurnya lebih cepat dari
rsync -a --delete
.Sumber:
sumber
rsync
bisa lebih cepat daripada biasarm
, karena itu menjamin penghapusan dalam urutan yang benar, sehingga perhitungan btress lebih sedikit diperlukan. Lihat jawaban ini serverfault.com/a/328305/105902-P
opsi ke rsync untuk beberapa tampilan lagi, juga, berhati-hatilah dengan sintaksisnya, garis miring tambahan wajib ada. Akhirnya, Anda dapat memulai perintah rsync pertama kali dengan-n
opsi pertama untuk meluncurkan menjalankan kering .-a
sama-rlptgoD
, tetapi untuk penghapusan hanya-rd
diperlukanSeseorang di Twitter menyarankan menggunakan
-delete
bukannya-exec rm -f{} \;
Ini telah meningkatkan efisiensi perintah, masih menggunakan rekursi untuk melalui semuanya.
sumber
find
miliki-delete
, dan lainnyafind
mungkin.-delete
harus selalu disukai-exec rm
bila tersedia, untuk alasan keamanan dan efisiensi.Bagaimana dengan sesuatu seperti:
find /path/to/folder -name "filenamestart*" -type f -print0 | xargs -0rn 20 rm -f
Anda dapat membatasi jumlah file untuk dihapus sekaligus dengan mengubah argumen untuk parameter
-n
. Nama file dengan kosong juga disertakan.sumber
-n 20
, karena xargs harus membatasi dirinya sendiri ke ukuran daftar argumen yang dapat diterima.man xargs
:(...) max-chars characters per command line (...). The largest allowed value is system-dependent, and is calculated as the argument length limit for exec
. Jadi-n
opsi untuk kasus-kasus seperti itu di mana xargs tidak dapat menentukan ukuran buffer CLI atau jika perintah yang dijalankan memiliki beberapa batasan.Trik yang cerdas:
Ini super CPU intensif, tetapi sangat cepat. Lihat https://web.archive.org/web/20130929001850/http://linuxnote.net/jianingy/en/linux/a-fast-way-to-remove-huge-number-of-files.html
sumber
rsync -a --delete
vs 43 untuklsdent
. Rasio 10x adalah untuktime ls -1 | wc -l
vstime ./dentls bigfolder >out.txt
(itu adalah perbandingan yang adil sebagian karena> file
vswc -l
).Memperluas salah satu komentar, saya tidak berpikir Anda melakukan apa yang Anda pikir Anda lakukan.
Pertama saya membuat sejumlah besar file, untuk mensimulasikan situasi Anda:
Kemudian saya mencoba apa yang saya harapkan gagal, dan apa yang Anda lakukan dalam pertanyaan:
Tapi ini tidak bekerja:
sumber
rm -Rf bigdirectory
beberapa kali. Saya memiliki direktori dengan ribuan jutaan subdirektori dan file. Saya bahkan tidak bisa menjalankanls
ataufind
ataursync
dalam direktori itu, karena kehabisan memori. Perintahrm -Rf
berhenti berkali-kali (kehabisan memori) hanya menghapus bagian dari miliaran file. Tetapi setelah banyak percobaan akhirnya berhasil. Tampaknya menjadi satu-satunya solusi jika kehabisan memori adalah masalahnya.Saya memiliki kesempatan untuk menguji
-delete
dibandingkan dengan-exec rm \{\} \;
dan bagi saya-delete
adalah jawaban untuk masalah ini.Menggunakan
-delete
menghapus file dalam folder 400.000 file setidaknya 1.000 kali lebih cepat daripadarm
.Artikel 'Cara menghapus banyak file di linux' menunjukkan bahwa ini sekitar tiga kali lebih cepat, tetapi dalam pengujian saya perbedaannya jauh lebih dramatis.
sumber
find -exec
mengeksekusirm
perintah untuk setiap file secara terpisah, itu sebabnya sangat lambat.Tentang
-delete
opsi di atas: Saya menggunakannya untuk menghapus sejumlah besar file (1M + est) di folder temp yang saya buat dan secara tidak sengaja lupa untuk membersihkannya setiap malam. Saya mengisi disk / partisi saya secara tidak sengaja, dan tidak ada yang bisa menghapusnya kecualifind .
perintahnya. Ini lambat, pada awalnya saya menggunakan:Tapi itu membutuhkan waktu yang EXTREME. Itu dimulai setelah sekitar 15 menit untuk menghapus beberapa file, tetapi tebakan saya adalah itu menghapus kurang dari 10 atau lebih per detik setelah akhirnya dimulai. Jadi, saya mencoba:
sebagai gantinya, dan saya membiarkannya berjalan sekarang. Tampaknya berjalan lebih cepat, meskipun itu sangat berat pada CPU yang perintah lainnya tidak. Sudah berjalan selama satu jam sekarang dan saya pikir saya mendapatkan ruang kembali pada drive saya dan partisi secara bertahap "melangsingkan" tetapi masih membutuhkan waktu yang sangat lama. Saya ragu itu berjalan 1.000 kali lebih cepat dari yang lain. Seperti dalam semua hal, saya hanya ingin menunjukkan pengorbanan dalam ruang vs waktu. Jika Anda memiliki bandwidth CPU untuk cadangan (kami lakukan) kemudian jalankan yang terakhir. Ini membuat CPU saya berjalan (
uptime
laporan):Dan saya telah melihat rata-rata beban lebih dari 30,00 yang tidak baik untuk sistem yang sibuk, tetapi untuk kita yang biasanya dimuat dengan ringan, tidak apa-apa selama beberapa jam. Saya telah memeriksa sebagian besar hal lain di sistem dan masih responsif sehingga kami OK untuk saat ini.
sumber
exec
Anda hampir pasti ingin tidak menggunakan-ls
dan melakukanfind . -type f -exec rm '{}' +
+ lebih cepat karena itu akan memberikan banyak argumen kepada rm karena dapat menangani sekaligus.find … -delete
melaluinice
atauionice
, yang dapat membantu. Jadi mungkin mengubah beberapa opsi pemasangan ke pengaturan yang kurang aman untuk kecelakaan. (Dan, tentu saja, tergantung pada apa lagi yang ada di sistem file, cara tercepat untuk menghapus semuanya sering kalimkfs
.)1
untuk mesin single-core sama dengan loadavg64
pada sistem 64-core - artinya setiap CPU sibuk 100% waktu.Ada beberapa metode yang dapat digunakan untuk menghapus sejumlah besar file di linux,. Anda dapat menggunakan find dengan opsi hapus, yang lebih cepat dari opsi exec. Kemudian Anda dapat menggunakan perl unlink, kemudian bahkan rsync. Cara menghapus sejumlah besar file di linux
sumber
Pertimbangkan untuk menggunakan volume Btrfs dan hapus seluruh volume untuk direktori semacam itu dengan banyak file.
Atau Anda dapat membuat file gambar FS kemudian unmount dan menghapus file untuk menghapus semuanya sekaligus dengan sangat cepat.
sumber
Dengan asumsi telah
parallel
menginstal GNU , saya telah menggunakan ini:parallel rm -rf dir/{} ::: `ls -f dir/`
dan itu cukup cepat.
sumber
Menghapus direktori yang BENAR-BENAR BESAR membutuhkan pendekatan yang berbeda, seperti yang saya pelajari dari situs ini - Anda harus menggunakan ionice. Ini memastikan (dengan -c3) bahwa penghapusan hanya akan dilakukan ketika sistem memiliki IO-waktu untuk itu. Sistem Anda memuat tidak akan naik ke tinggi dan semuanya tetap responsif (meskipun waktu CPU saya untuk menemukan cukup tinggi sekitar 50%).
sumber
+
bukannya\;
akan membuat ini lebih cepat karena melewati lebih banyak argumen untuk rm sekaligus, kurang forkingionice -c3 find <dir> -type f -delete
harus berfungsi di dalam folder utama
sumber
ls
tidak akan berfungsi karena jumlah file di folder. Ini sebabnya saya harus menggunakanfind
, terima kasih.ls -f
, yang menonaktifkan penyortiran. Penyortiran mengharuskan seluruh direktori dimuat ke dalam memori untuk disortir. Yang tidak disortirls
harus dapat mengalirkan outputnya.find . -print0 | xargs -0 rm
, yang akan menggunakan char NULL sebagai pemisah nama file.Untuk petunjuk Izkata di atas:
Ini hampir berhasil - atau mungkin berhasil - tetapi saya memiliki beberapa masalah dalam izin; file ada di server, tetapi saya masih tidak mengerti dari mana masalah izin ini berasal. Bagaimanapun, Terminal meminta konfirmasi pada setiap file. Jumlah file sekitar 20.000, jadi ini bukan pilihan. Setelah "-r" saya menambahkan opsi "-f", jadi seluruh perintahnya adalah " rm -r -f foldername / ". Kemudian itu tampaknya bekerja dengan baik. Saya seorang pemula dengan Terminal, tapi saya kira ini tidak apa-apa, kan? Terima kasih!
sumber
Tergantung pada seberapa baik Anda perlu menyingkirkan file-file itu, saya sarankan menggunakan
shred
.jika Anda ingin membersihkan direktori, tetapi Anda tidak dapat menghapusnya dan membuatnya kembali, saya sarankan memindahkannya dan membuatnya kembali secara instan.
ini lebih cepat, percaya atau tidak, karena hanya satu inode yang harus diubah. Ingat: Anda tidak dapat benar-benar memparalelkan rasa ini di komputer multicore. Itu datang ke akses disk, yang dibatasi oleh RAID atau apa pun.
sumber
shred
tidak akan bekerja dengan banyak filesystem modern.Jika Anda memiliki jutaan file dan setiap solusi di atas membuat sistem Anda stres, Anda dapat mencoba inspirasi ini:
File
nice_delete
:Dan sekarang hapus file:
Temukan akan membuat kumpulan (lihat
getconf ARG_MAX
) beberapa puluh ribu file dan meneruskannyanice_delete
. Ini akan membuat batch yang lebih kecil untuk memungkinkan tidur ketika kelebihan terdeteksi.sumber
Jika Anda hanya ingin menyingkirkan banyak file sesegera mungkin
ls -f1 /path/to/folder/with/many/files/ | xargs rm
mungkin bekerja dengan baik, tetapi lebih baik jangan jalankan di sistem produksi karena sistem Anda mungkin menjadi masalah IO dan aplikasi mungkin macet selama operasi penghapusan.Script ini berfungsi dengan baik untuk banyak file dan seharusnya tidak mempengaruhi ioload sistem.
sumber
Gunakan
rm -rf directory
sebagai gantirm -rf *
.Kami awalnya melakukan
rm -rf *
sementara di direktori untuk menghapus konten dan berpikir itu secepat mungkin. Tapi kemudian, salah satu insinyur senior kami menyarankan agar kami tidak menggunakan tanda bintang (*
) dan meneruskannya di direktori induk, sepertirm -rf directory
.Setelah beberapa perdebatan sengit tentang bagaimana itu tidak akan membuat perbedaan, kami memutuskan untuk membandingkannya, bersama dengan metode penggunaan ketiga
find
. Inilah hasilnya:rm -rf directory
sekitar 9 KALI LEBIH CEPAT daripadarm -rf *
!Singkatnya, kami membeli bir untuk insinyur itu!
Jadi sekarang kita gunakan
rm -rf directory; mkdir directory
untuk menghapus direktori dan membuatnya kembali.sumber