Guida avanzata di scripting Bash: Un'approfondita esplorazione dell'arte dello scripting di shell | ||
---|---|---|
Indietro | Appendice C. Una breve introduzione a Sed e Awk | Avanti |
Awk è un linguaggio completo per l'elaborazione di testo, con una sintassi che ricorda quella del C. Sebbene possegga un'ampia serie di funzionalità e di operatori, qui ne verranno analizzati solo un paio - quelli più utili allo scripting di shell.
Awk suddivide ogni riga dell'input che gli è stato passato in campi. Normalmente, un campo è una stringa di caratteri consecutivi separati da spazi, anche se esistono opzioni per modificare il delimitatore. Awk, quindi, analizza e agisce su ciascun singolo campo. Questo lo rende ideale per trattare file di testo strutturati -- in particolare le tabelle -- e dati organizzati in spezzoni logici, come righe e colonne.
Negli script di shell, i segmenti di codice awk vengono racchiusi da apici singoli (quoting forte) e da parentesi graffe.
echo uno due | awk '{print $1}' # uno echo uno due | awk '{print $2}' # due awk '{print $3}' $nomefile # Visualizza allo stdout il campo nr.3 del file $nomefile. awk '{print $1 $5 $6}' $nomefile # Visualizza i campi nr.1, 5 e 6 del file $nomefile. |
Si è appena visto il comando print di awk in azione. L'altra sola funzionalità di awk di cui è necessaria la spiegazione sono le variabili. Awk le tratta in modo simile a come sono gestite negli script di shell, anche se con una maggiore flessibilità.
{ totale += ${numero_colonna} } |
numero_colonna
al totale di totale
. Infine, per visualizzare
"totale", vi è il comando di blocco di
codice END, da eseguire dopo che lo script
ha elaborato completamente il proprio input.
END { print totale } |
Corrispondente ad END, vi è BEGIN, per il blocco di codice che deve essere eseguito prima che awk inizi l'elaborazione del suo input.
L'esempio seguente illustra come awk permetta di incrementare il numero di strumenti di verifica di testo a disposizione dello scripting di shell.
Esempio C-1. Conteggio delle occorrenze di lettere
#! /bin/sh # letter-count.sh: Conta le occorrenze di lettere in un file di testo. # # Script di nyal (nyal@voila.fr). # Usato con il permesso dell'autore. # Ricommentato dall'autore di questo libro. # Versione 1.1: Modificata per funzionare con gawk 3.1.3. # (Funziona anche con le versioni precedenti.) INIT_TAB_AWK="" # Parametro per inizializzare lo script awk. conteggio=0 FILE_INDICATO=$1 E_ERR_PARAM=65 utilizzo () { echo "Utilizzo: letter-count2.sh file lettere" 2>&1 # Per esempio: ./letter-count2.sh nomefile.txt a b c exit $E_ERR_PARAM # Parametri passati allo script insufficienti. } if [ ! -f "$1" ] ; then echo "$1: File inesistente." 2>&1 utilizzo # Visualizza il messaggio di utilizzo ed esce. fi if [ -z "$2" ] ; then echo "$2: Non è stata specificata nessuna lettera." 2>&1 utilizzo fi shift # Le lettere sono state specificate. for lettera in `echo $@` # Per ognuna . . . do INIT_TAB_AWK="$INIT_TAB_AWK tab_search[${conteggio}] = \"$lettera\";\ final_tab[${conteggio}] = 0; " # Passato come parametro al successivo script awk. conteggio=`expr $conteggio + 1` done # DEBUGGING: # echo $INIT_TAB_AWK; cat $FILE_INDICATO | # Il file viene collegato, per mezzo di una pipe, al seguente script awk. # -------------------------------------------------------------------------------- # La versione precedente dello script usava: # awk -v tab_search=0 -v final_tab=0 -v tab=0 -v nb_letter=0 -v chara=0 -v chara2=0 \ awk \ "BEGIN { $INIT_TAB_AWK } \ { split(\$0, tab, \"\"); \ for (chara in tab) \ { for (chara2 in tab_search) \ { if (tab_search[chara2] == tab[chara]) { final_tab[chara2]++ } } } } \ END { for (chara in final_tab) \ { print tab_search[chara] \" => \" final_tab[chara] } }" # -------------------------------------------------------------------------------- # Niente di così complicato, solo . . . #+ cicli for, costrutti if e un paio di funzioni specializzate. exit $? # Confrontate questo script con letter-count.sh. |
Per dimostrazioni più semplici dell'uso di awk negli script di shell, vedi:
Questo è tutto, per quanto riguarda awk, ma vi sono moltissime altre cose da imparare. Si vedano i relativi riferimenti in Bibliografia.