Ada banyak situasi di mana penggunaan a *
hampir tidak dapat dihindari - misalnya rm -rf *
dalam folder yang menampung ribuan subfolder dan file.
Tetapi bagaimana jika Anda ingin mengecualikan hanya satu atau dua file atau folder dari rm
perintah? Saya sudah menelusuri Google dan hanya menemukan solusi yang cukup rumit seperti yang find . -depth -not \( -name 'one' -o -name 'two' \
-o -name 'three' \) -exec rm {} \;
dinyatakan di sini .
Apakah ada kemungkinan untuk melakukan ini dengan cara yang lebih mudah - tanpa jalan memutar ke sana find
? Misalnya rm -rf --exclude='one' --exclude='two' --exclude='three' *
suka di rsync atau hanya rm -rf -e 'one','two','three' *
?
Mungkin bahkan kemungkinan umum untuk mengecualikan hal-hal dari *
(perintah sehingga lainnya seperti cp
, mv
, ... tidak harus melaksanakan sendiri)? Sesuatu seperti *{'one','two','three'}
itu?
sumber
find
dengan--delete
opsi (tidak perlu mengeksekusirm
untuk setiap file. Itu overhead yang tidak perlu).mv -t /tmp one two three && rm -rf * && mv -t . /tmp/one /tmp/two /tmp/three
, tapi saya lebih suka solusi yang memberikan kemungkinan untuk secara eksplisit mengecualikan sesuatu dari*
. Pasti akan ada situasi di mana memindahkan atau menyalin file ke tujuan lain tidak akan menjadi pilihan.Jawaban:
Untuk Bash ada opsi shell yang disebut
extglob
yang dinonaktifkan secara default untuk menjaga kompatibilitas dengan sintaks shell standar. Extglob melengkapi sintaks oleh operator tambahan seperti!()
,?()
,@()
dan beberapa lagi.Untuk menghidupkan
extglob
, ketikkanshopt -s extglob
. Untuk mengaktifkannya untuk tipe pengguna saat iniecho 'shopt -s extglob' >> ~/.bashrc
.Untuk contoh rm: Dengan
extglob
Anda dapat menggunakansumber
shopt
benda itu ke dalam diri Anda~/.bashrc
, tidak ada salahnya.*
sama sekali, tetapi malah menambahkan indikator serupa (seperti!
) yang memiliki fungsi tambahan? Dalam hal ini akan menjadi solusi yang bagus.Saya telah membangun kecuali untuk itu (sry bahwa saya belum dapat menambahkan dokumentasi).
Saya punya folder seperti ini:
Mengetik
except b d
akan memberi Andaa
danc
Sekarang Anda dapat menyalurkannya ke
rm
.Ini mungkin sulit untuk diingat, jadi mengapa tidak membuat skrip di atas kecuali, yang disebut
rm-except
:Demikian pula mudahnya adalah
ls-except
:sumber
Sebagai alternatif untuk extglob (meskipun itu adalah jawaban yang sangat bagus dan semua orang seharusnya ada
shopt -s extglob globstar
di .bashrc), Anda dapat menggunakan variabel global $ GLOBIGNORE . Katakanlah Anda ingin mendapatkan setiap file kecuali 'foo.txt' dan 'bar baz.txt':... Namun, ini akan mengaktifkan opsi shell
dotglob
, yang berarti*
akan cocok dengan file yang dimulai dengan titik (yang biasanya disembunyikan). Jadi Anda sebenarnya membutuhkan dua perintah:Karena ini adalah variabel global, itu akan memengaruhi setiap bola yang Anda gunakan sampai $ GLOBSTAR tidak disetel baik dengan keluar atau dengan
Ini juga hanya akan bekerja pada string literal yang diteruskan ke variabel. Anda dapat melihat apa yang saya maksud dengan menetapkan $ GLOBIGNORE dan melihat perbedaan antara perintah-perintah ini:
sumber