Melhor maneira de iterar através do seguinte comando awk

0

Eu tenho a seguinte declaração awk

awk '/^string$/{i=1;next} i && i++ <= 2' file

Isto irá procurar pela string e então imprimir 2 linhas abaixo.

Então, como exemplo

$ cat file
string
aaa
bbb
ccc

$ awk '/^string$/{i=1;next} i && i++ <= 2' file
$ bbb

O que eu quero fazer é mudar o 2 em um contador, para que eu possa repetir 10 linhas a cada vez. Por exemplo

for i in {1..5}
do
   awk '/^111$/{i=1;next} i && i++ <= $i' file
done

Isso, obviamente, não funciona e não tenho certeza se isso é possível, já que o comando está encapsulado no loop.

Para referência, o que eu quero fazer é verificar dentro de um arquivo de configuração (file.cfg) por um valor [header] e ver se uma variável está habilitada (variable = enabled)

Por exemplo

cat file.cfg
[header]
# nothing
variable = enabled

Eu acho que os principais atributos são que [cabeçalho] estará em uma linha indeterminada (poderia ser a linha 1, poderia ser a linha 122)

E a variável nem sempre será a segunda linha depois do [cabeçalho], algumas pessoas podem colocar 7 posições abaixo, outras 2 posições abaixo.

Espero que faça sentido e obrigado antecipadamente.

    
por devnull 22.06.2015 / 18:20

2 respostas

1

Se o seu arquivo de configuração for criado usando [header] lines seguido por variable=value lines, você poderá usar o seguinte comando para obter todos os valores de uma seção específica:

sed -n '/^\[header\]/,/^\[/p' /path/to/file.cfg|grep -vE '?\s?[;#]'

A parte sed filtrará todas as linhas de [header] até (e incluindo) a próxima linha, começando com um caractere [ . O comando grep filtrará as linhas que têm ; ou # como caractere inicial.

Em vez de sed, você pode usar awk . Com base em uma resposta anterior à pergunta link :

awk '/\[header\]/{print; flag=1; next}/\[/{flag=0}flag' file.cfg

Você pode acrescentar o comando grep como acima se quiser filtrar as linhas comentadas.

    
por 22.06.2015 / 20:16
1

No shell você pode concatenar strings se elas forem justapostas sem espaços intermediários, por exemplo:

echo 'abc$def'"and so on"
abc$defand so on

Portanto, no seu exemplo, simplesmente saia da string (') e inicie uma string (") para que $i pode ser interpolado pelo shell:

awk '/^111$/{i=1;next} i && i++ <= '"$i" file

Além disso, se as strings [header] forem facilmente distinguíveis dos dados linhas, você pode apenas usar a habilidade do awk para executar um comando quando entre dois linhas. Por exemplo:

seq 10 | awk '/6/,/9/{print}'

imprimirá as linhas 6 a 9. Então, ao invés de fazer sua própria contagem, e assumindo [header1] é uma sintaxe típica de cabeçalho (então você precisa escapar do [ ), você poderia usar algo como

awk '/^\[header1]/,/^\[header2]/ { print }'
    
por 22.06.2015 / 19:59

Tags