Pengganti case preserving dalam Vim


154

Bisa ini dilakukan di Vim?

Yang saya maksud adalah: mencari 'BadJob' dan mengganti dengan 'GoodJob' akan melakukan penggantian berikut

'badjob' -> 'goodjob'  
'BadJob' -> 'GoodJob'  
'badJob' -> 'goodJob'  
'BADJOB' -> 'GOODJOB'

16
Ini harus menjadi fitur vim. Sangat masuk akal.
— Bach

Jawaban:


120

Gunakan abolish.vim :

:%S/badjob/goodjob/g

13
Kami tidak pantas menerima Paus Tim.
— Andrew Keeton

1
Plugin ini sepertinya tidak berfungsi untuk saya. Jika saya menyukai kata BadJobdan ingin menggantinya GoodJob, saya tidak dapat menggunakannya %S/badjob/goodjob/g. Gagal mendeteksi kecocokan.
— Roymunson

@Roymunson Yang perlu Anda lakukan adalah ini:, %S/BadJob/GoodJob/gmaka perintah Subvert akan beralih ke mode case campuran dan akan melakukan semua substitusi seperti yang diberikan oleh OP.
— shivams

28

Saya tidak tahu apakah ini jenis solusi yang Anda cari ... tetapi saya telah menggunakan ini: keepcase.vim

Tidak ada dukungan di vim ...


11

tentu kamu bisa

:s/\cbad/\= strpart(submatch(0), 0 ,1) == toupper(strpart(submatch(0), 0, 1)) ? "GOOD" : "good"/

ps. Saya menebak keepcase.vim merangkum beberapa logika yang sama :)


Ya itu sejak 2007::% SubstituteCase / \ cbadjob / GoodJob / g ^^
— Luc Hermitte

Berarti sejak gVim 7.2? Saya mencobanya di gVim 7.1 (12-Mei-2007) dan itu tidak berhasil :(
— fc.

Tidak, saya telah menambahkan perintah: SubstituteCase ke plugin pada 2007. Itu saja. Plugin ini tersedia di vim.org, dan tidak dikirimkan dengan vim seperti biasanya dengan sebagian besar plugin.
— Luc Hermitte

1. Ini gagal ketika pengguna memilikinya :set ignorecase. 2. Badakan diganti dengan GOODalih-alih Good. 3. " job" Bagian dari pertanyaan diabaikan, jadi ini juga akan menggantikan lambada→ lamgooda. Perbaikan dan penjelasan untuk bug ini dan beberapa hal lain dalam jawaban saya . (Juga LOLOWL!)
— Aaron Thoma

7

Anda dapat menempel dan mengadaptasi ini:
(Tentu saja, jika Anda melakukan ini dari waktu ke waktu, Anda akan menginginkan plugin alih-alih keburukan ini. Tetapi bagi beberapa yang terburu-buru dan hanya membutuhkannya sekali, ini adalah hack cepat untuk kesenangan menyisipkan Anda :)

:%s/\cbad\zejob/\= ( submatch(0)[0] is# toupper(submatch(0)[0]) ? 'G' : 'g' ) . ( submatch(0)[1] is# toupper(submatch(0)[1]) ? 'OOD' : 'ood' )

Terlepas dari pola pencarian, Anda harus mengedit empat 'string 'dalam kode pengganti: Edit bagian-bagian dengan huruf tebal :

:% s / \ c bad \ ze job / \ =
(submatch (0) [0] adalah # toupper (submatch (0) [0])? ' G ': ' g ').
(submatch (0) [1] adalah # toupper (submatch (0) [1])? ' OOD ': ' ood ')

Jangan gunakan versi 'oranye' ini untuk menempel, karena karakter linebreak-nya juga akan melanggar perintah.

/\zeadalah vim regex sintaksis gula untuk menandai lookahead positif: Pola setelah \zediperiksa, tetapi tidak diganti.


is#?? Biarkan saya jelaskan ... (Jika tertarik.)

#(juga dalam ==#dan lainnya ) memberlakukan sensitivitas kasus. Kalau tidak, dengan :set ignorecase(yang saya gunakan, karena itu diperlukan untuk berguna :set smartcase), vim akan mempertimbangkan 'a' == 'A'!!

Gila apa adanya, kita harus memperhitungkannya: Karena ini tergantung pada pengaturan pengguna, ==haruskah NEVAR digunakan! (Kecuali di mana itu akan menjadi yang Anda inginkan.) Saya bahkan akan mengikuti rekomendasi untuk digunakan ==#ketika membandingkan bilangan bulat: http://learnvimscriptthehardway.stevelosh.com/chapters/22.html#code-defensive

is#alih-alih ==#adalah cara pengkodean lain secara defensif: Ini meningkatkan keamanan tipe: http://google.github.io/styleguide/vimscriptguide.xml?showone=Type_checking#Type_checking
Ini harus digunakan saat membandingkan dengan string literal.

'single-quoted'alih-alih "double quoted" string adalah praktik lain yang baik: http://google.github.io/styleguide/vimscriptguide.xml?showone=Strings#Strings


HT @fc. - jawaban ini dibangun berdasarkan jawaban mereka , memperbaiki beberapa kekurangan.


4

Jika Anda hanya mencocokkan string (tidak tergantung kasus) yang tepat dengan beberapa kapitalisasi yang mungkin, kemungkinan lain adalah:

:s/abc/\={'abc':'xyz','Abc':'Xyz'}[submatch(0)]/i

2

Alternatif untuk plugin keepcase adalah SmartCase - mengganti kata-kata sambil menyimpan case aslinya . (Jangan biarkan diri Anda patah semangat dengan peringkat buruk.)


1
Apakah ada trik untuk mempersingkat yang sulit diingat dan membosankan untuk mengetik perintah seperti :%s/file\A\?size/\=SmartCase("LastModifiedTime")/ig?
— Michael Härtl

@ MichaelHärtl: Anda dapat menggunakan :SmartCaseperintah. Saya telah memperpanjang itu di garpu saya sendiri . Perhatikan bahwa ini membutuhkan perpustakaan-ingo sebagai ketergantungan.
— Ingo Karkat
Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.