Memindahkan file, dan meminta pengguna ketika ada nama duplikat:
Seperti yang ditunjukkan oleh Subv3rsion dan Eric Leschinski , -newermt
predikat memilih file yang dimodifikasi lebih baru dari tanggal (dan waktu opsional) yang ditentukan sebagai operandnya. Untuk menemukan file
- di mana saja di
srcdir
(yaitu, termasuk subdirektori, subdirektori, dll.)
- terakhir diubah pada (misalnya) September 2014
- dan pindahkan ke
destdir
... Anda dapat menjalankan:
find srcdir -type f -newermt 2014-08-31 ! -newermt 2014-09-30 -exec mv -i {} destdir/ \;
Dalam -exec
ekspresi, temukan melewati nama file yang ditemukan di {}
. ;
menandakan -exec
bahwa perintah yang akan dijalankan, dan argumennya, semuanya telah disediakan (dalam hal ekspresi selanjutnya dilewatkan untuk menemukan setelah -exec
argumen predikat tertentu - lihat di bawah untuk contoh ini). ;
harus lolos karena \;
tidak ditafsirkan secara khusus oleh shell. (Tanpa \
, ;
akan mengakhiri seluruh find
perintah, bekerja sama dengan baris baru. Meskipun find
perintah ini tidak memiliki apa-apa setelah -exec
ungkapan ini , gagal melewati ;
argumen masih merupakan kesalahan sintaksis.)
Jika Anda hanya ingin membuat daftar file - yang disarankan jika Anda tidak yakin bagaimana email lama disimpan atau file lain apa yang ada - hilangkan -exec
dan semuanya di sebelah kanannya. (Untuk email, seringkali email dari tanggal berbeda disimpan dalam file yang sama ; untuk seseorang dalam situasi yang dijelaskan dalam pertanyaan di sini, saya sarankan menyelidiki bagaimana mereka disimpan sebelum memindahkan file apa pun.) Jika Anda ingin mencetak nama mereka dan memindahkannya mereka, tambahkan -print
sebelumnya -exec
.
mv -i
meminta kapan saja file akan ditimpa di tujuan, seperti yang akan terjadi jika:
- file dengan nama yang sama ada dari cadangan sebelumnya, atau
- file dengan nama yang sama tetapi dari subdirektori yang berbeda
srcdir
telah dipindahkan selama find
operasi yang sama , atau
- (paling tidak mungkin) file dengan nama yang sama dibuat di suatu tempat
srcdir
selama find
operasi yang sama , setelah dokumen asli dipindahkan tetapi tidak lama kemudian ditemukan setelah find
melintasi subdirektori yang berbeda.
Cara lain untuk memohon rm
:
Anda memiliki opsi lain untuk bagaimana menangani file dengan nama duplikat.
- Tanpa
-i
(yaitu, ), biasanya tidak meminta persetujuan, tetapi akan melakukannya jika file tujuan hanya-baca. ( Bahkan kadang-kadang bisa berhasil menimpa file read-only, seperti jika pengguna yang menjalankannya memiliki file tersebut.)mv {} destdir/
mv
mv
- Jika Anda tidak ingin bahkan tingkat interaktivitas itu, dan ingin
mv
selalu (berusaha untuk) menimpa file yang bernama identik, gunakan mv -f
.
- Sebaliknya, jika Anda ingin melewatkan file sumber ketika sudah ada file tujuan dengan nama yang sama, gunakan
mv -n
.
mv
menerima -b
dan --backup
menandai untuk secara otomatis mengganti nama file dengan nama identik yang sudah ada di tujuan. Secara default ~
ditambahkan untuk menghasilkan nama cadangan, dan jika file dengan nama dan file dengan nama cadangan sudah ada di tujuan, file cadangan akan ditimpa. Default ini dapat ditimpa oleh opsi yang diteruskan saat memohon mv
, dan oleh variabel lingkungan. Lihat man mv
detailnya, dan contoh di bawah ini.
Memindahkan file dan membuat cadangan jika nama duplikat:
Untuk memindahkan semua file, buat cadangan file dengan nama duplikat menggunakan ~
sufiks, dan gunakan sufiks bernomor ketika file sudah ada (sehingga untuk menghindari menimpa apa pun), jalankan:.~n~
.~
find srcdir -type f -newermt 2014-08-31 ! -newermt 2014-09-30 -exec mv --backup=existing {} destdir/ \;
Jika Anda melewatkan file dengan nama duplikat dan ingin tahu yang mana:
Jika Anda menggunakan mv -n
dan ingin tahu file mana yang tidak dipindahkan karena ada file lain dengan nama yang sama, cara terbaik mungkin hanya dengan menjalankan find
perintah asli lagi, tanpa -exec
dan semuanya di sebelah kanannya. Ini akan mencetak nama mereka.
Ini juga akan mencetak nama-nama file yang cocok yang dibuat sejak Anda menjalankan find .... -exec ...
perintah asli , tetapi untuk aplikasi ini biasanya tidak ada karena Anda mencari file dengan waktu modifikasi lama. Dimungkinkan untuk memberikan file stempel waktu modifikasi yang lebih tua dari usia sebenarnya, dengan touch
dan mekanisme lainnya, tetapi itu sepertinya tidak akan terjadi dalam kasus ini tanpa sepengetahuan Anda.
Mengetahui segera saat file dilewati karena nama rangkap:
mv -n
tidak melaporkan, atau mengembalikan kode keluar khusus , ketika itu menahan diri untuk memindahkan file. Jadi, jika Anda ingin segera diberi tahu tentang file-file yang dilewati saat find
berjalan, Anda harus membuat langkah terpisah untuk itu. Salah satu caranya adalah:
find srcdir -type f -newermt 2014-08-31 ! -newermt 2014-09-30 -exec mv -n {} destdir/ \; \
-exec [ -f {} ] \; -exec printf "\`%s' skipped (exists in \`%s')\\n" {} destdir \;
Beberapa pertimbangan teknis yang mungkin kecil: Peringatan ini salah jika mv
gagal menyalin file karena alasan yang berbeda dari yang ada di tujuan dan keluar dari kesuksesan pelaporan . Sepertinya tidak mungkin, tapi saya tidak yakin itu tidak mungkin. Itu juga berpotensi menderita kondisi balapan : itu akan memperingatkan ketika tidak ada kesalahan sama sekali, jika file baru dengan nama yang sama dibuat di tempat yang sama selama waktu yang sangat singkat setelah file lama dipindahkan dan sebelum pemeriksaan untuk lihat apakah sudah dihapus. (Mempertimbangkan aplikasi, saya ragu kedua masalah itu akan benar-benar terjadi.) Bisa ditulis ulang untuk memeriksa tujuan sebelumnyamemindahkan file alih-alih setelah: maka kondisi balapan akan berhubungan dengan file tujuan yang baru dibuat alih-alih file sumber. Dan sementara kesalahan dan peringatan yang dilaporkan oleh find
atau mv
(atau [
, meskipun seharusnya tidak ada) akan ditulis ke kesalahan standar , ...skipped (exists in...
peringatan kami akan ditulis ke output standar . Biasanya keduanya muncul di terminal Anda, tetapi ini mungkin penting jika Anda membuat skrip.
Saya telah membagi perintah itu menjadi dua baris agar lebih mudah dibaca. Itu dapat dijalankan dengan cara itu, atau Anda dapat menghapus \
dan baris baru (yaitu, baris istirahat).
Bagaimana cara find
kerja perintah itu?
find
predikat dapat berupa tes (seperti -type
dan -newermt
), digunakan untuk nilai pengembaliannya, atau tindakan (seperti -print
dan -exec
), yang sering digunakan untuk efek sampingnya.
Ketika tidak ada operator (seperti -a
untuk dan , -o
untuk atau ) disediakan antara ekspresi, -a
tersirat. find
mempekerjakan evaluasi hubung singkat untuk dan dan atau . (Yaitu, ) benar hanya jika ekspresi p dan q keduanya benar, jadi q tidak perlu dievaluasi jika p salah. Meskipun kita sering tidak memikirkannya dalam istilah ini, inilah mengapa tes harus benar untuk tindakan selanjutnya atau tes untuk dievaluasi. Misalnya, misalkan muncul pada direktori. Itu mengevaluasi ke false, sehingga dapat melewati semuanya setelah itu.p q
p -a q
find
-type f
Seperti halnya tes, tindakan juga mengevaluasi benar atau salah. Dengan cara ini, -exec
melaporkan jika perintah yang dijalankan keluar melaporkan keberhasilan (benar) atau gagal (salah). Kami memiliki rantai -exec
ekspresi ini yang terhubung dengan implisit dan :
-exec mv -n {} destdir/ \; -exec [ -f {} ] \; -exec printf "\`%s' skipped (exists in \`%s')\\n" {} destdir \;
Ini mencoba untuk memindahkan file, dan jika mv
laporan gagal, berhenti. Kami tidak ingin memperingatkan tentang file yang dilompati dengan benar jika ada masalah lain mengapa tidak dipindahkan.
Tapi jika berhasil, itu kemudian berjalan dengan [
perintah . Seperti find
, [
mendukung jenis ekspresinya sendiri yang diteruskan sebagai argumen. [ -f {} ]
memeriksa apakah operan setelah -f
(diteruskan ke find
tempatnya {}
) ada (dan merupakan file biasa), dan mengembalikan benar / berhasil atau salah / gagal.
(Status keluar banyak perintah paling baik ditafsirkan sebagai menandakan keberhasilan atau kegagalan, tetapi [
status yang ada biasanya ditafsirkan sebagai benar atau salah.)
Jika [
dikembalikan false, maka file hilang, jadi dipindahkan, jadi tidak perlu melakukan apa pun. Tetapi jika [
dikembalikan false, file tersebut masih ada. Kemudian find
mengevaluasi -exec
ekspresi berikutnya , yang mencetak pesan peringatan.
Bacaan lebih lanjut