2012-09-04 12 views
7

di recente ho scoperto che questo semplice sed espressione funzionano bene su Linux o sotto Cygwin, ma non su Mac con un errore "label indefinito":sed "Etichetta non definita" su MacOS

$ sed '/SUCCESSFUL/d ; /\[java\]/!b label; s/\s\+\[java\]//; /^\s*$$/d; /Compiling/!d; :label /^\s*$$/d; s/^/monitor: /' 
sed: 1: "/SUCCESSFUL/d ; /\[java ...": undefined label 'label; s/\s\+\[java\]//; /^\s*$$/d; /Compiling/!d; :label /^\s*$$/d; s/^/monitor: /' 

sed su MacOS è un Variante BSD con diverse opzioni rispetto alla controparte GNU. Tuttavia, man sed indica chiaramente che la versione MacOS di sed supporta le etichette, quindi perché questo errore e, soprattutto, come risolverlo?

risposta

3

Il nome dell'etichetta termina con il primo newline letterale, non a virgola. Ci sono due semplici modi per risolvere il problema. Aggiungere a capo letterale:

sed '/SUCCESSFUL/d 
    /\[java\]/!b label 
    s/\s\+\[java\]// 
    /^\s*$$/d; /Compiling/!d 
    :label 
    /^\s*$$/d 
    s/^/monitor: /' 

oppure utilizzare le opzioni -e:

sed -e '/SUCCESSFUL/d ; /\[java\]/!b label' \ 
    -e 's/\s\+\[java\]//; /^\s*$$/d; /Compiling/!d' \ 
    -e':label' -e'/^\s*$$/d; s/^/monitor: /' 
2

Ci sono un sacco di domande simili su SO, ma la maggior parte di esse è dovuta al comportamento di -i diverso tra piattaforme, quindi questo è diverso.

In questo caso, il problema è piuttosto semplice: sembra che i riferimenti all'etichetta possano tornare indietro solo nella versione BSD di sed, mentre la versione GNU consente di utilizzare i riferimenti avanzati. Questo è su MacOS, lo :label deve apparire prima del il b label.

La soluzione è di riscrivere l'espressione per definire l'etichetta prima del ramo o, nel caso dell'espressione precedente, realizzare che il ramo è una specie di "se questo modello non è presente ... vai avanti". In questo caso, l'espressione può essere espansa e non è necessario l'etichetta in primo luogo:

sed '/SUCCESSFUL/d ; /\s+\[java\]\s*/d; /\[java\]/s/\s\+\[java\]//; /Compiling/!d; /^\s*$$/d; s/^/monitor: /' 
+0

+1 e Buona cattura. Aiuta anche a visualizzare il problema come codice indentato, invece che con una sola frase :-) Buona fortuna. – shellter