Pega cada coluna que contém múltiplos espaços?

2

Meu arquivo:

subnet 172.25.10.0 netmask 255.255.255.0 {
option domain-name-servers 172.25.10.9, 8.8.8.8;
default-lease-time 300;
max-lease-time 7500;
range dynamic-bootp 172.25.10.10 172.25.10.30 ;
option broadcast-address 172.25.10.255;
option routers 172.25.10.1;
option ip-forwarding off;
}

para cada campo eu quero o text part sozinho e o value part sozinho :( Eu não sei os campos e quantos espaços em cada um, a mesma coisa para valores)

conforme notamos:

Campos:

max-lease-time;(o space)
option domain-name-servers (1 space)

Valores:

300(o space)

172.25.10.10 172.25.10.30 ( 1 space)

Meu outpput desejado é:

Eu quero colocar os valores em uma variável com o nome dos campos:

domain-name-servers="172.25.10.9, 8.8.8.8"(eliminate 'option')
default-lease-time="300"

e assim por diante

awk não funciona para mim, porque existem alguns valores com espaços: 172.25.10.9, 8.8.8.8

posso alcançar minha meta usando grep -o ?

    
por user78050 17.08.2014 / 15:55

1 resposta

2

Eu não acho que você possa substituir um = usando grep onde ele não existe no texto original; no entanto, supondo que sua versão do grep suporte as extensões PCRE, você poderia separar os pares nome-valor da seguinte forma

grep -oP '(option |range )?\K(\S+) (.+?(?=;))'

Se você quiser a substituição, você pode usar o perl simples, por exemplo,

perl -pe 's/(option |range )?(\S+) (.+?);/$2="$3"/' file
subnet 172.25.10.0 netmask 255.255.255.0 {
domain-name-servers="172.25.10.9, 8.8.8.8"
default-lease-time="300"
max-lease-time="7500"
dynamic-bootp="172.25.10.10 172.25.10.30 "
broadcast-address="172.25.10.255"
routers="172.25.10.1"
ip-forwarding="off"
}

[Você não é específico sobre o que você quer fazer com as linhas de abertura e fechamento, então deixei-as como estão]

ou, mais ou menos equivalente com sed

sed -E 's/(option |range )?([^[:space:]]{1,}) (.*);/=""/' file

ambos dividem a expressão em 3 grupos consistindo de, respectivamente

  • string opcional que consiste em options ou range seguido por um único espaço
  • uma sequência não vazia de caracteres não espaciais (seguida por um único espaço)
  • zero ou mais caracteres (seguidos por ; )

e, em seguida, substitua apenas os segundo e terceiro grupos, com o sinal = e aspas duplas adicionadas. Em um aplicativo real, você provavelmente deve tentar tornar essas expressões mais robustas, por exemplo, substituindo quaisquer espaços únicos por seqüências de comprimento não zero de POSIX [[:space:]] caracteres (ou seja, espaços e / ou tabulações).

Observe que, em todos os casos, é assumido que somente os campos value podem conter espaços; Supõe-se que os campos name (como default-lease-time ) consistam em caracteres que não são espaços em branco. Não acho que exista uma maneira lexical de manipular o caso em que ambos campos possam conter espaços em branco não citados arbitrários.

    
por 17.08.2014 / 16:53