2011-09-18 14 views
11

miei dati è della forma:Come eliminare testo dopo un simbolo specificato in Vim

id|name|things that I don't care 

Quindi per ogni linea che voglio eliminare il testo dopo il secondo | simbolo.

Come si fa a Vim con un comando?

Edit:

ci sono in realtà i tubi in più dopo la seconda |, dal momento che la | viene utilizzato come delimitatore per le colonne.

risposta

18

Una soluzione:

:%s!^\([^|]*|\)\{2\}\zs.*!! 

Spiegazione:

  • %: su ogni linea
  • s: subtitute
  • !: inizio reticolo
  • ^: inizio della linea
  • \(: inizio del gruppo
  • [^|]*: qualsiasi numero di caratteri non tubi
  • |: seguito da un tubo
  • \): fine del gruppo
  • \{2\}: abbinare due accuse di quel gruppo
  • \zs: avviare il pattern matching qui
  • .*: qualsiasi carattere
  • !: fine del modello e iniziare la sostituzione
  • !: fine della sostituzione

Questo lascerà intatte le linee con meno di due tubi e tratterà anche wi le linee che hanno più dei due tubi ...

Prima

id name things that I don't care no pipes 
id|name things that I don't care one pipe 
id|name|things that I don't care two pipes 
id|name|things that I don't care extra pipe at line end| 
id|name|things that I don't care | extra pipe mid-line 
id|name|things that I don't| care| two extra pipes 
name|things that I don't care missing first column and pipe 
|name|things that I don't care missing first column 

Dopo:

id name things that I don't care no pipes 
id|name things that I don't care one pipe 
id|name| 
id|name| 
id|name| 
id|name| 
name|things that I don't care missing first column and pipe 
|name| 
+1

Grazie per la demo di '\ zs' –

+0

@Michael Dunn: Sei il benvenuto! – Johnsyweb

+1

Spiegazione molto approfondita! –

0

vorrei fare qualcosa di simile:

%s/\(.*|.*|\).*/\1 

Yeap, che ha funzionato:

yeap

+3

Solo se ci sono esattamente due tubi sulla linea, perché "le cose che non mi interessa" potrebbero avere solo una pipa ... forse ... non si sa mai. :) #nitpicking –

1

Se il "do not care" parte non ha i tubi, poi

:%s/|[^|]*$/|/ 

che si occupa anche di parti vuote "non importa". E continua a funzionare se aggiungi nuovi campi prima della parte "non importa".

11

si può semplicemente ripetere un comando modalità Normale che salta al carattere successivo alla seconda | simbolo e cancella fino alla fine della linea per ciascuna delle linee.

:%norm!2f|lD 
+1

Questo è davvero molto bello. Molto meglio [VimGolf] (http://vimgolf.com/) punteggio oltre alla mia risposta! – Johnsyweb

+1

@Johnsyweb: Grazie! Direi che è più naturale, dal momento che segue il flusso di editing casuale, semplicemente ripetendo i comandi che uno usa per eseguire l'attività su una riga. –

0

:%s/[^|]*|[^|]*|\zs.*//

Una variante di ciò che abbiamo già visto.

Abbina molti "non pipe" seguiti da pipe, due volte. Sostituisci con niente a partire dalla seconda pipe (\ zs).

+0

Questo cancella la seconda pipe, non solo "testo dopo il secondo simbolo '|' "." – Johnsyweb

+1

Lo so. Ho cercato di essere intelligente. Leggendo quel tubo è il separatore di colonne. Ho pensato che non c'era bisogno di uno alla fine perché non ce n'è uno all'inizio. Avrei dovuto dirlo sul testo però. – johnny

Problemi correlati