Aprenda como usar os padrões especiais do Awk ‘BEGIN and END’ – Parte 9
Na Parte 8 desta série do Awk, introduzimos alguns recursos poderosos de comando do Awk, ou seja, variáveis, expressões numéricas e operadores de atribuição.
À medida que avançamos, neste segmento, cobriremos mais recursos do Awk, e esses são os padrões especiais: BEGIN
e END
.
Esses recursos especiais serão úteis à medida que tentamos expandir e explorar mais métodos de construção de operações Awk complexas.
Para começar, vamos voltar nossos pensamentos para a introdução da série Awk, lembre-se que quando iniciamos esta série, eu indiquei que a sintaxe geral de um Awk é executado > comando é:
awk 'script' filenames
E na sintaxe acima, o script Awk tem o formato:
/pattern/ { actions }
Quando você considera o padrão no script, normalmente é uma expressão regular; além disso, você também pode pensar no padrão como padrões especiais BEGIN
e END
. Portanto, também podemos escrever um comando Awk no formato abaixo:
awk '
BEGIN { actions }
/pattern/ { actions }
/pattern/ { actions }
……….
END { actions }
' filenames
Caso você use os padrões especiais: BEGIN
e END
em um script Awk, isto é o que cada um deles significa:
- Padrão BEGIN: significa que o Awk executará as ações especificadas em BEGIN uma vez antes de qualquer linha de entrada ser lida.
- Padrão END: significa que o Awk executará as ações especificadas em END antes de realmente sair.
E o fluxo de execução de um script de comando Awk que contém esses padrões especiais é o seguinte:
- Quando o padrão
BEGIN
é usado em um script, todas as ações para BEGIN são executadas uma vez antes de qualquer linha de entrada ser lida. - Em seguida, uma linha de entrada é lida e analisada nos diferentes campos.
- Em seguida, cada um dos padrões não especiais especificados é comparado com a linha de entrada para uma correspondência. Quando uma correspondência é encontrada, as ações para esse padrão são então executadas. Esta etapa será repetida para todos os padrões que você especificou.
- A seguir, os estágios 2 e 3 são repetidos para todas as linhas de entrada.
- Quando todas as linhas de entrada forem lidas e tratadas, caso você especifique o padrão
END
, a(s) ação(ões) serão executadas.
Você deve sempre se lembrar desta sequência de execução ao trabalhar com padrões especiais para obter os melhores resultados em uma operação Awk.
Para entender tudo, vamos ilustrar usando o exemplo da parte 8, sobre a lista de domínios de propriedade da Tecmint, armazenada em um arquivo chamado domains.txt.
news.linux-console.net
linux-console.net
linuxsay.com
windows.linux-console.net
linux-console.net
news.linux-console.net
linux-console.net
linuxsay.com
linux-console.net
news.linux-console.net
linux-console.net
linuxsay.com
windows.linux-console.net
linux-console.net
cat ~/domains.txt
Neste exemplo, queremos contar quantas vezes o domínio linux-console.net
está listado no arquivo domains.txt. Então escrevemos um pequeno script shell para nos ajudar a fazer isso usando a ideia de variáveis, expressões numéricas e operadores de atribuição que tem o seguinte conteúdo:
#!/bin/bash
for file in $@; do
if [ -f $file ] ; then
#print out filename
echo "File is: $file"
#print a number incrementally for every line containing linux-console.net
awk '/^linux-console.net/ { counter+=1 ; printf "%s\n", counter ; }' $file
else
#print error info incase input is not a file
echo "$file is not a file, please specify a file." >&2 && exit 1
fi
done
#terminate script with exit code 0 in case of successful execution
exit 0
Vamos agora empregar os dois padrões especiais: BEGIN
e END
no comando Awk no script acima como segue:
Vamos alterar o script:
awk '/^linux-console.net/ { counter+=1 ; printf "%s\n", counter ; }' $file
Para :
awk ' BEGIN { print "The number of times linux-console.net appears in the file is:" ; }
/^linux-console.net/ { counter+=1 ; }
END { printf "%s\n", counter ; }
' $file
Depois de fazer as alterações no comando Awk, o script de shell completo agora se parece com isto:
#!/bin/bash
for file in $@; do
if [ -f $file ] ; then
#print out filename
echo "File is: $file"
#print the total number of times linux-console.net appears in the file
awk ' BEGIN { print "The number of times linux-console.net appears in the file is:" ; }
/^linux-console.net/ { counter+=1 ; }
END { printf "%s\n", counter ; }
' $file
else
#print error info incase input is not a file
echo "$file is not a file, please specify a file." >&2 && exit 1
fi
done
#terminate script with exit code 0 in case of successful execution
exit 0
Quando executamos o script acima, ele primeiro imprimirá a localização do arquivo domains.txt, depois será executado o script de comando Awk, onde o BEGIN
padrão especial nos ajuda a imprimir a mensagem “O número de vezes que linux-console.net aparece no arquivo é:
” antes que qualquer linha de entrada seja lida no arquivo.
Então nosso padrão, /^linux-console.net/
é comparado com cada linha de entrada e a ação, { counter+=1 ; }
é executado para cada linha de entrada, que conta o número de vezes que linux-console.net
aparece no arquivo.
Por fim, o padrão END
imprimirá o total de vezes que o domínio linux-console.net
aparece no arquivo.
./script.sh ~/domains.txt
Para concluir, examinamos mais recursos do Awk explorando os conceitos de padrão especial: BEGIN
e END
.
Como mencionei antes, esses recursos do Awk nos ajudarão a construir operações de filtragem de texto mais complexas, há mais para abordar nos recursos do Awk e na parte 10, abordaremos o idéia das variáveis integradas do Awk, então fique conectado.