skapad 2001 · komplexitet basic · version 6.0
Vim tillhandahåller :s
(ersättare) kommando för sök och ersätt; detta tips visar exempel på hur man byter ut. På vissa system har gvim Find and Replace på menyn Redigera (: help: promptrepl), men det är lättare att använda kommandot :s
på grund av kommandoradshistoriken och förmågan att infoga text (till exempel ordet under markören) till sök- eller ersättningsfälten.
Grundläggande sökning och ersätt
Kommandot :substitute
söker efter ett textmönster och ersätter det med en textsträng. Det finns många alternativ, men det här är vad du antagligen vill ha:
:s/foo/bar/g
Hitta varje förekomst av ”foo” (endast i den aktuella raden) och ersätt den med ”bar ”.:%s/foo/bar/g
Hitta varje förekomst av ”foo” (i alla rader) och ersätt den med ”bar”.:%s/foo/bar/gc
Ändra varje ”foo” till ”bar”, men be först om bekräftelse.:%s/\<foo\>/bar/gc
Ändra endast hela ord som exakt matchar ”foo” till ”bar”; be om bekräftelse.:%s/foo/bar/gci
Ändra varje ”foo” (skiftlägeskänslig på grund avi
-flaggan) till ”bar”; be om bekräftelse.:%s/foo\c/bar/gc
är detsamma eftersom\c
gör sökfelet okänsligt. Detta kan vara önskvärt efter att ha använt:set noignorecase
för att göra sökningar skiftlägeskänsliga (standard).:%s/foo/bar/gcI
Ändra varje ”foo” (skiftlägeskänslig på grund avI
-flaggan) till ”bar”; be om bekräftelse.:%s/foo\C/bar/gc
är detsamma eftersom\C
gör sökfrågan känslig. Det kan vara önskvärt efter att ha använt:set ignorecase
för att göra sökningar skiftlägeskänsliga.
Flaggan g
betyder global – varje förekomst i raden ändras snarare än bara den första. Detta tips antar standardinställningen för alternativet "gdefault"
och "edcompatible"
(av), vilket kräver att g
flagga inkluderas i %s///g
för att utföra ett globalt substitut. Att använda :set gdefault
skapar förvirring eftersom %s///
är global, medan %s///g
inte är det (det vill säga , g
vänder om innebörden).
När du använder flaggan c
måste du för varje match bekräfta vad att göra. Vim kommer att mata ut något som: replace with foobar (y/n/a/q/l/^E/^Y)?
(där foobar är ersättningsdel för kommandot :s/.../.../
. Du kan skriva y
vilket betyder att ersätta denna match, n
för att hoppa över denna match, a
för att ersätta denna och alla återstående matchningar ( ”alla” återstående matchningar), q
för att avsluta kommandot, l
för att ersätta denna match och avsluta (tänk på ”sista”), ^E
för att bläddra upp skärmen genom att hålla ned Ctrl-tangenten och trycka på E och ^Y
för att bläddra ned skärmen genom att hålla ned Ctrl-tangenten och trycka på Y. De sista två alternativen är dock bara tillgängliga om din Vim är en normal, stor eller stor byggnad eller om insert_expand-funktionen var aktiverad vid kompileringstid (leta efter +insert_expand
i utgången av :version
).
Även när du använder flaggan c
hoppar Vim till t den första matchen hittar den från början av bufferten och uppmanar dig att bekräfta att du ska byta ut den matchen. Vim tillämpar IncSearch
markeringsgruppen på den matchade texten för att ge dig en visuell ledtråd om vilken match den fungerar på (ställ in på reverse
som standard för alla tre termtyperna enligt Vim 7.3). Dessutom, om mer än en matchning hittas och du har sökmarkering aktiverad med :set hlsearch
, markerar Vim de återstående matchningarna med Search
markeringsgruppen . Om du använder sökmarkering bör du se till att dessa två markeringsgrupper skiljer sig visuellt eller så kommer du inte att kunna se vilken match Vim uppmanar dig att byta ut.
Detaljer
Sökintervall:
Obs: Från och med Vim 7.3 tillämpas substitutioner på ett område som definieras av märken eller ett visuellt urval (som använder en speciell typ av märken ”< och ”>) är som standard inte begränsade av kolumnpositionen. I stället tillämpar Vim ersättningen för hela raden där varje märke visas såvida inte\%V
atom används i mönstret som::"<,">s/\%Vfoo/bar/g
.
När du söker:
.
,*
,\
,anger en / samling. Teckenintervall kan representeras med en
-
; till exempel en bokstav a, b, c eller siffran 1 kan matchas med. Negera samlingen med
matchar alla tecken utom a, b, c eller 1.
\{#\}
används för upprepning./foo.\{2\}
matchar foo och de två följande tecknen.\
krävs inte vid stängningen}
så/foo.\{2}
kommer att göra samma sak.\(foo\)
gör en bakre referens till foo. Parentes utan flykt matchas bokstavligen. Här krävs\
för att stänga\)
.
När du byter ut:
\r
är ny linje, är\n
en nullbyte (0x00).\&
är ampersand (& är texten som matchar sökmönstret).\0
infogar texten som matchas av hela mönstret\1
infogar texten för den första bakreferensen.\2
infogar den andra bakre referensen och så vidare.
Du kan använda andra avgränsare med ersättning:
:s#http://www.example.com/index.html#http://example.com/#
Spara skrivning med \zs
och \ze
för att ställa in början och slutet på ett mönster. Till exempel istället för:
:s/Copyright 2007 All Rights Reserved/Copyright 2008 All Rights Reserved/
Använd:
:s/Copyright \zs2007\ze All Rights Reserved/2008/
Använd det aktuella ordet eller register
:%s//bar/g
Byt ut varje matchning i det senaste sökmönstret med ”bar”. Du kan till exempel först placera markören på ordetfoo
och sedan trycka på*
för att söka efter det ordet. Ovanstående ersättare skulle då ändra alla ord som exakt matchar ”foo” till ”bar”.
:%s/foo/<c-r><c-w>/g
Ersätt varje förekomst av ”foo” med ordet under markören.<c-r><c-w>
betyder att du trycker på Ctrl-R och sedan Ctrl-W. Ordet under markören infogas som om du skrev det.:%s/foo/<c-r><c-a>/g
Ersätt varje förekomst av ”foo” med WORD under markören (avgränsad med mellanslag).<c-r><c-a>
betyder att du trycker på Ctrl-R och sedan Ctrl-A. WORD under markören infogas som om du skrev det.:%s/foo/<c-r>a/g
Ersätt varje förekomst av ”foo” med innehållet i registret ”a”.<c-r>a
betyder att du trycker på Ctrl-R och sedana
. Innehållet i registret ”a” kommer att infogas som om du skrev det.:%s/foo/<c-r>0/g
Samma som ovan, med hjälp av register 0 som innehåller texten från det senaste yank-kommandot. Exempel på kommandon för yank (copy) äryi(
som kopierar texten inom parentes runt markören ochy$
som kopierar texten från markören till slutet av raden. Efter ett yank-kommando som inte specificerade ett destinationsregister kan den kopierade texten matas in genom att trycka på Ctrl-R och sedan0
.:%s/foo/\=@a/g
Ersätt varje förekomst av ”foo” med innehållet i registret ”a”.\=@a
är en referens för att registrera ”a”. Innehållet i registret ”a” visas inte i kommandot. Detta är användbart om registret innehåller många textrader.:%s//<c-r>//g
Byt ut varje matchning i det senaste sökmönstret med/
-registret (det senaste sökmönstret). Efter att ha tryckt på Ctrl-R och sedan/
för att infoga det sista sökmönstret (och innan du trycker på Enter för att utföra kommandot) kan du redigera texten för att göra alla ändringar som krävs.:%s/<c-r>*/bar/g
Ersätt alla förekomster av texten i systemets urklipp (i*
-registret) med ”bar” (se nästa exempel om flerlinje) . I vissa system är att välja text (i Vim eller ett annat program) allt som krävs för att placera texten i*
-registret.:%s/<c-r>a/bar/g
Ersätt alla förekomster av texten i registret ”a” med ”bar”.<c-r>a
betyder att du trycker på Ctrl-R och sedana
. Innehållet i registret ”a” kommer att infogas som om du skrev det. Nya rader i register ”a” infogas som^M
och hittas inte. Sökningen fungerar om varje^M
manuellt ersätts med ”\ n” (två tecken: backslash, ”n”). Denna ersättning kan utföras medan du skriver kommandot::%s/<c-r>=substitute(@a,"\n","\\n","g")<CR>/bar/g
"\n"
(dubbla citat) representerar den nya raden med enstaka tecken;"\\n"
(enkla citat) representerar två snedstreck följt av ”n
”.Funktionensubstitute()
utvärderas av uttrycksregistret<c-r>=
(Ctrl-R=
); den ersätter varje ny rad med ett enda snedstreck följt av ”
n
”.<CR>
indikerar att du trycker på Enter för att avsluta=
-uttrycket.:%s/<c-r>0/bar/g
Samma som ovan, med hjälp av register 0 som innehåller texten från det senaste yank-kommandot.
Se Klistra in register i sök- eller kolonkommandon istället för att använda urklipp.
Ytterligare exempel
:%s/foo/bar/
Byt ut den första förekomsten på varje rad av ”foo” med ”bar”.:%s/.*\zsfoo/bar/
På varje rad ersätter du den sista förekomsten av ”foo” med ”bar”.:%s/\<foo\>//g
Ta bort alla förekomster av hela ordet ”foo” på varje rad.:%s/\<foo\>.*//
På varje rad raderar du hela ordet ”foo” och all följande text (till slutet av raden).:%s/\<foo\>.\{5}//
På varje rad raderar du den första förekomsten av hela ordet ”foo” och följande fem tecken.:%s/\<foo\>\zs.*//
På varje rad raderar du all text efter hela ordet ”foo” (till slutet av raden).:%s/.*\<foo\>//
Ta bort hela ordet ”foo” och all föregående text (från början av raden) på varje rad.:%s/.*\ze\<foo\>//
På varje rad raderar du all text som föregår hela ordet ”foo” (från början på rad).:%s/.*\(\<foo\>\).*/\1/
Radera all text som föregår och följer hela ordet ”foo” på varje rad.:%s/\<foo\(bar\)\@!/toto/g
På varje rad ersätter du varje förekomst av ”foo” (som startar ett ord och inte följs av ”bar”) med ”toto”.:s/^\(\w\)/\u\1/
Om det första tecknet i början av den aktuella raden endast är gemener, växlar du det till versaler med\u
(se växling av tecken ).:%s/\(.*\n\)\{5\}/&\r/
Infoga en tom rad var femte rad. Mönstret söker efter\(.*\n\)
(valfri rad inklusive dess radslut) upprepas fem gånger (\{5\}
). Ersättaren är&
(texten som hittades), följt av\r
(newline).:%s/\<foo\(\a*\)\>/\=len(add(list, submatch(1)))?submatch(0):submatch(0)/g
Få en lista med sökresultat. (listan måste finnas) Ställer inmodified
-flaggan på grund av ersättningen, men innehållet är oförändrat. Obs: Med en nyligen tillräcklig Vim (version 7.3.627 eller högre) kan du förenkla detta till::%s/\<foo\(\a*\)\>/\=add(list, submatch(1))/gn
Detta har fördelen att bufferten inte kommer att markeras modifierad och ingen extra ångra-tillstånd skapas. Uttrycket i ersättningsdelen körs i sandlådan och får inte ändra bufferten.
Specialfall
För att ersätta mönster med motsvarande skiftlägeskänslig text, Michael Geddes ” s Keepcase-plugin kan användas, t.ex.:
:%SubstituteCase/\cHello/goodBye/g
Ersätt ”Hej hej helLo HELLO” med ”Adjö adjö goodBye GOODBYE”
För att ändra förskjutningarna i en patchfil (radnummer i ett block), det här lilla utdraget kan användas:
s/^@@ -\(\d\+\),\(\d\+\) +\(\d\+\),\(\d\+\) @@$/\="@@ -".eval(submatch(1)+offsetdiff).",".submatch(2)." +".eval(submatch(3)+offsetdiff).",".submatch(4)." @@"/g
Användbart när vi vill ta bort några block från en patch, utan att patch behöver klaga på skillnader i offset.
Obs Bör försöka göra uttrycket mer kompakt, men vet inte hur utan att ha möjlighet att ändra oönskade rader.
Se även: använda ersättning
- 63 Tillämpa ersättare till ett visuellt block
- 81 Ersätta tecken och rader enkelt
- 159 Tangenttryckning Spara ersättning och sökning
- 406 Alternativa avgränsare för ersättaren kommando
- 438 Sök och ersätt i ett visuellt val
- 464 Sök och ersätt ordet under markören
- 479 Ersätt utan att skriva
- 573 Upprepa en ersättning från aktuell markörposition
- 605 Ersätt ett ord med den ryckade texten
- 654 Specialtecken i ersättningskommandot
- 755 Använda ett uttryck i ersättningskommando
- 808 Ersätt ett visuellt textblock med ett annat sådant block
- 915 Använd g istället för att ersätta
- 971 Ersätt med ökande siffror
- 1114 Stegsteg och ersätt
- 1501 Ersätt senaste sökning
Se även: ersätt i buffertar / filer
- 382 Sök och ersätt i flera buffertar
- : hjälp: ersätt
- : hjälp cmdline-r anges
- : hjälpmönster
- : hjälp ”gdefault”
- : hjälpregister
ATT GÖRA
The stort ”se även” -avsnitt kan vara användbart för läsare. Vi måste slå samman några av de relaterade tipsen (men gör inte resultatet för komplicerat). Jag inkluderade tipsnumren för att hjälpa redaktörer att hålla koll. hanteras genom att söka och sedan ändra manuellt (och trycka på .
för att upprepa den senaste ändringen). Dessutom kan du bestämma hur du ska ändra varje instans.Se Kopiera eller ändra sökträff för en teknik där du kan trycka på n
för att hitta nästa instans, skriv sedan cs
för att ändra sökträff till vad som helst.
Har det nyligen skett en förändring av hur% s fungerar? På något sätt kan jag använda både < cr > och \ = @ som ersättare, men jag kan inte använda dem som sökningar och ersättare.
Om du beskriver exakt vad du gör och vad som händer kan jag kanske hjälpa även om jag ställer frågor. JohnBeckett (diskussion) 02:15, 1 juni 2019 (UTC)