Vim: s bir satırdaki ilk N <g oluşumunu değiştirir


13

Vim'de bazen bir maçın ilk birkaç tekrarını bir çizgi üzerinde değiştirebilirim, ancak her biri böyle golmaz. Örneğin:

a a a a a

için

b b b a a

Kullanabileceğimi biliyorum :s/a/b/[enter]:[up][enter]:[up][enter], ama bu üç tekrarda yeterince sıkıcı, potansiyel olarak 10'dan fazla oyuncu değişikliği olan çizgilerim var.
Denedim:

  • :s/a/b/3g: vim sondaki karakterlerden şikayet etti.
  • :s/a/b/3: bu ve sonraki iki satırdaki ilk olayı değiştirir.
  • 3:s/a/b: öncekiyle aynı.
  • :s/a/b/g3: bu ve sonraki iki satırdaki tüm tekrarlamaları değiştirir.
  • :3s/a/b: 3. satırdaki ilk olayı değiştirir.
  • :/a/,3/a/s/a/b: dosyada bulunan sonraki ave üçüncü satır arasındaki her satırdaki ilk tekrarlamayı değiştirir a(gerekirse tersine çevirmeyi ister).
  • :/a/,/\([^a]*a\)\{3\}/s/a/b/: bu ile sonraki arasındaki her satırdaki ilk oluşumu 3 as ile değiştirir (ve bu çok karakterli bir aramaya kolayca genişletilemezdi).

Ve hiçbiri işe yaramayan diğer adresleme kalıpları. Söylemeliyim ki, :sbu soruna bir cevap bulmaya çalışan komuta hakkında adil bir miktar öğrendim , ama hala çözemedim.

Bunu nasıl yapacağını bilen var mı?

(belirli aralık için bonus puanlar, örneğin ikinci ila dördüncü tekrarlar)


2
Bunu vim'de yapamayacağınızdan eminim, ama daha az sıkıcı hale getirmek için "n" ve "hakkında bilginiz var mı? görsel modda mı? Yani, / pattern / komutunu kullanarak değiştireceğiniz şeyi bulursunuz, "cw" kullanarak değiştirirsiniz ya da her neyse, sonraki deseni bulmak ve "hit" tuşuna basmak için "n" (sadece n, tırnak yok) kullanırsınız. (sadece nokta, tırnak işareti yok) son düzenlemeyi gerçekleştirmek için.
Bruce Ediger

@BruceEdiger Bildim nve .burada kullanmayı düşünmemiştim. Kesinlikle bir gelişme, teşekkürler.
Kevin

s/a/=something/hile yapmalı ( :help sub-replace-=). Vim'de hemen somethingyarasa yazacak kadar akıcı değilim .
Gilles 'SO- kötü olmayı bırak'

Not: :[up][enter]ile değiştirilebilir &hala ideal değildir ama en azından daha az ağrılı olan.
Kowh

Yanıtlar:


10

Bina :s/pattern/replacement/gc fikri Samus_ gelen tek bir satırda 4 oluşumları aracılığıyla 2nd yerine, (görünüyor desen yedek dizesi içinde bulunur Doğru çalışmasını sağlamak için en basit yol olarak):

:call feedkeys("nyyyq") | s/pat/string/gc

feedkeys()giriş dizesini klavye giriş kuyruğuna dolduran bir işlevdir. Önemli olan sayımı önceden yapmaktır, böylece sayıyı kaybetme veya kesintiye uğrama konusunda endişelenmenize gerek kalmaz.

Daha genel bir durum için, Mth ila Nth oluşumlarını tek bir satırda N için çok büyük bir M'den büyük veya ona eşit olarak değiştirmek :

:call feedkeys(repeat("n", M-1) . repeat("y", N-M+1) . "q") | s/pat/string/gc

M ve N'yi istediğiniz değerlerle değiştirin (kendiniz vimyapmak istemiyorsanız önemsiz zihinsel aritmetiği bile yapabilirsiniz). Not .VIML dize birleştirme operatörüdür. Açıkçası bu sadece büyük M için tuş vuruşlarını kaydeder . Bu işlevi sık sık kullanırsanız, yukarıdakileri yazmak için biraz fazla olduğu için, yukarıdakileri bir tür özel komut veya işleve koymak için zaman kazanabilirsiniz.


Hmm. Bunu beğendim. Bunun için de bir işlev yazabilmeliyim.
Kevin

8

İlk soru için yapardım:

:s/a/b
&&

İkincisi daha hileli, otomatik olarak yapmanın bir yolunu bilmiyorum ama her maçta vim istemini şu şekilde yapabilirsiniz:

:s/a/b/gc

Daha sonra ilk n maçına "hayır" ve diğerlerine "evet" yanıtı verirsiniz.


Hmm, unuttum c, bu henüz önerilen en iyi çözüm olabilir. Hala saymak zorundayım, ama arama dizesini içeren değiştirmelerle çalışacak ilk seçenek olduğunu düşünüyorum.
Kevin

6
a a a a a
a a a a a
a a a a a
a a a a a
a a a a a
a a a a a
a a a a a

:3,6g/^/let i=0 | while i<3 | s/a/b/ | let i+=1 | endwhile

a a a a a
a a a a a
b b b a a
b b b a a
b b b a a
b b b a a
a a a a a

1
Bu iyi, ama yine de Gilles'in işaret ettiği problemden muzdarip (o zamandan beri silinmiş gibi görünen başka bir yazıda), sadece değiştirme kalıbı içermiyorsa işe yarıyor. Ben senaryo fikrini seviyorum.
Kevin

Güzel şey!
piskopos

1

Bence bu işe yarayabilir, önce değiştirin, sonra 2 kez tekrarlayın:

:s/a/b/
2@:
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.