Posso excluir apenas a primeira linha correspondente usando sed?

Posso excluir apenas a primeira linha correspondente usando sed?

Eu tenho um arquivo testfile.txtcontendo

pippo=x
pluto=y
1234=z

Eu gostaria de excluir apenaso primeirocorrespondência de linha /^[a-z]\+=/(a primeira linha neste exemplo).

Já tentei com o seguinte comando mas sem sucesso:

sed   '/^[a-z]\+=/,+0d' testfile.txt

mas o primeirodoislinhas são excluídas.

Existe uma maneira de fazer essa tarefa usando sed?

Cumprimentos

Responder1

O problema com seu sedcomando

$ sed '/^[a-z]\+=/,+0d' testfile.txt

é que o sedscript é aplicado atodolinha dos dados de entrada.

O +0(que é uma extensão GNU) significa que seu script é equivalente a

$ sed '/^[a-z]\+=/d' testfile.txt

e a primeira e a segunda linhas seriam excluídas, como você percebeu.

Aliás, você obterá exatamente o mesmoefeitousando +1, mas por outros motivos. O dcomando seria, em vez de ser aplicado às linhas um e dois individualmente, seria aplicado às duas primeiras linhas por causa da correspondência na primeira linha (ou seja, o intervalo do dcomando seria as linhas um e mais uma +1). Isso não exclui a linha três porque está fora do intervalo.

sedA solução GNU

$ sed '0,/^[a-z]\+=/{//d}' testfile.txt

aquele usuário @Whitefield postou funciona e é bastante bom (embora a -ropção seja desnecessária e o 0endereço inicial possa ser alterado 1neste caso, se você quiser ser mais POSIX).

Uma variante BSD sedda mesma abordagem seria semelhante

$ sed '1,/^[a-z]+=/{/^[a-z]+=/d
  }' testfile.txt

Escapar de the +só é necessário se você sedimplementar "expressões regulares básicas obsoletas" em vez de "expressões regulares básicas modernas". Tanto o BSD sedquanto o GNU sedno meu sistema (Mac OS X) parecem ser do tipo "moderno". POSIX não tem essa distinção, e ler os manuais ( re_format(7)no BSD, que faz essa distinção) e a especificação POSIX lado a lado faz minha cabeça girar.

Responder2

@John1024 Sinto muito, mas sua solução só funciona se a primeira linha correspondente for a primeira linha do arquivo.

Resolvi o problema com o código a seguir sed -r '0,/^[a-z]\+=/{//d;}' testfile.txt, mas ainda estou convencido de que minha solução anterior deveria ter funcionado mesmo com posix sed.

Na verdade, a idéia era fornecer como endereço de segunda linha um deslocamento de 0 linhas... mas ainda exclui também a linha seguinte, isso parece um bug.

do man sedUbuntu 14.04

... addr1,+N Irá corresponder a addr1 e às N linhas seguintes a addr1. ...

informação relacionada