Quero excluir duas linhas consecutivas específicas que correspondem a padrões de uma linha específica de um arquivo.
Por exemplo, o conteúdo do arquivo é como abaixo.
Line1: a
Line2: b
Line3: c
Line4: Name: 123
Line5: xyz
Line6: Name: 456
Line7: abc
Quero encontrar as linhas começando na linha 4, correspondendo ao padrão da 1ª linha começando com "Nome:" e correspondendo ao padrão da 2ª linha começando com espaço em branco e exclua as duas linhas consecutivas.
Alguma maneira eficiente de fazer isso no shell usando sed
ou algo mais?
Para ser um pouco mais claro, quero remover as informações de assinatura/soma de verificação do MANIFEST.MF.
Exemplo MANIFEST.MF como abaixo: Do arquivo de manifesto abaixo, desejo remover a entrada "Nome:". onde a entrada "Nome:" pode estar em uma linha ou em 2 (ou mais) linhas.
Inicialmente, minha solução foi encontrar a primeira entrada "Nome:" seguida pela entrada "SHA-256-Digest:" e excluir até o final do arquivo. Infelizmente, esta solução tem o problema de remover uma entrada necessária no meio. Por exemplo, "NetBeans-Simply-Convertible:" também está sendo removido.
Então, agora quero remover a entrada "Nome:" se estiver disponível em 1 linha ou se a entrada abranger 2 ou mais linhas. Mas não devo perder entradas como "NetBeans-Simply-Convertible:" ao remover entradas "Nome:".
Já estou removendo as entradas "SHA-256-Digest:" com o comando abaixo no arquivo comsed -i "/^\SHA-256-Digest: /d" $manifest_file
Manifest-Version: 1.0
Version-Info: ....
Name: com/abc/xyz/pqr/client/relationship/message/notifier/Relati
onshipUpdateNotifierFactory.class
SHA-256-Digest: cSSyk6Y2L2F9N6FPtswUkxjF2kelMkGe4bFprcQ+3uY=
Name: com/abc/xyz/pqr/client/relationship/ui/BaseRelationshipView
$5.class
SHA-256-Digest: w9HgRjDuP024U4CyxeKPYFe6rzuzxZF3b+9LVG36XP8=
Name: com/abc/xyz/pqr/client/impl/MofRelationshipAgentImpl.class
SHA-256-Digest: GwIBIU+UdPtjyRhayAVM90Eo+SwCT/kP65dI59adEnM=
Name: com/abc/xyz/pqr/client/settings/ConvertibleProperties.class
NetBeans-Simply-Convertible: {com/abc/xyz/pqr/client/settings}Con
vertibleProperties
SHA-256-Digest: 5FszAtfpPXcLx/6FBWbfeg6E4fwFMRozV+Q+3rReATc= ...
Resultado esperado:
Manifest-Version: 1.0
Version-Info: ....
NetBeans-Simply-Convertible: {com/abc/xyz/pqr/client/settings}Con
vertibleProperties
...
Responder1
estranhoabordagem:
Digamos que temos o seguinte arquivo de entrada file.txt
(considerando que cada linha contém Line<number>:
o primeiro campo):
Line1: a
Line2: b
Line3: c
Line4: Name: 123
Line5: xyz
Line6: Name: 456
Line7: abc
Line8: Name: 111
Line9: www
Line10: Num: 222
Line11: abc
Line12: Name: 333
Line13: ccc
awk '{ if ($2 == "Name:") {
if ((getline l) > 0){
if (l ~ /^\S+ \S+/) { next } else { print $0 RS l }
}
} else { print }
}' file.txt
A saída:
Line1: a
Line2: b
Line3: c
Line8: Name: 111
Line9: www
Line10: Num: 222
Line11: abc
'getline var'- lê o próximo registro da entrada do awk na variávelvar
OObter linhaO comando retorna 1 se encontrar um registro e 0 se encontrar o final do arquivo.
Responder2
Você vê que o que você está perguntando não está claro: uma resposta exclui 4 linhas (as duas correspondentes e as duas subsequentes); outro apaga tudomasas linhas correspondentes...
Vou acrescentar o que entendo que você deseja: excluo 2 linhas, a que corresponde Name: 123
e a subsequente. Eu faço isso com sed
:
sed -e '/Name: 123/{N;d}' filename
Responder3
Usando ed
:
$ printf '%s\n' 'g/^ / s///\' '-,.j' 'g/^Name: /d' 'g/SHA-256-Digest: /d' '4,$g/^$/d' ,p Q | ed -s file
Manifest-Version: 1.0
Version-Info: ....
NetBeans-Simply-Convertible: {com/abc/xyz/pqr/client/settings}ConvertibleProperties
Isso aplica o seguinte script de edição ao seu arquivo de entrada:
g/^ / s///\
-,.j
g/^Name: /d
g/SHA-256-Digest: /d
4,$g/^$/d
,p
Q
Isso consiste em seis comandos separados:
Os dois comandos
s///
são-,. j
aplicados a cada linha que começa com um caractere de espaço. A expressão regular vazia nos
comando reutiliza a expressão^
dog
comando anterior (que é usado para aplicar um ou mais comandos a linhas que correspondem a uma expressão regular), portanto, os
comando remove o primeiro espaço vazio nas linhas que começam com espaços vazios. Oj
comando então une a linha modificada com a linha anterior. Isso desfaz efetivamente a quebra das linhas nos dados de entrada.O comando
d
é aplicado a todas as linhas que começam comName:
, removendo-as.Da mesma forma, as linhas que começam com
SHA-256-Digest:
são removidas.As linhas vazias são removidas da linha 4 em diante.
Enviamos o buffer completo para a saída padrão para exibir o resultado.
Q
sai do editor incondicionalmente (você pode usarwq
para gravar as alterações de volta no arquivo original).
Responder4
sed -e '
4,$!d; # skip non-relevant portion
/Name:/N; # grab the line coming after Name:
/\n.* /d; # what we were after is not this
P;D
' yourfile