Una guida pratica per imparare awk
Ottieni una migliore gestione del comando awk scaricando il nostro eBook gratuito.
Di tutti i comandi Linux disponibili (e ce ne sono molti), i tre più essenziali sembrano essere sed
, awk
e grep
. Forse è il suono arcano dei loro nomi, o l'ampiezza del loro potenziale utilizzo, o semplicemente la loro età, ma quando qualcuno fornisce un esempio di comando "Linux", di solito è uno di questi tre. E mentre sed
e grep
hanno diversi semplici standard di una riga, il meno prestigioso awk
rimane costantemente prominente per essere particolarmente sconcertante.
Probabilmente utilizzerai sed
per una rapida sostituzione della stringa o grep
per filtrare un modello su base giornaliera. È molto meno probabile che tu componga un comando awk
. Spesso mi chiedo il perché di ciò e lo attribuisco ad alcune cose. Prima di tutto, molti di noi usano a malapena sed
e grep
se non per qualche variazione su questi due comandi:
$ sed -e 's/foo/bar/g' file.txt
$ grep foo file.txt
Quindi, anche se potresti sentirti più a tuo agio con sed
e grep
, potresti non sfruttare tutto il loro potenziale. Naturalmente non c'è alcun obbligo di saperne di più su sed
o grep
, ma a volte mi chiedo come "imparo" i comandi. Invece di imparare come funziona un comando, spesso imparo un incantesimo specifico che include un comando. Di conseguenza, spesso sento una falsa familiarità con il comando. Penso di conoscere un comando perché posso nominare tre o quattro opzioni a mente, anche se non so cosa fanno le opzioni e non riesco a mettere il dito sulla sintassi.
E questo è il problema, credo, che molte persone affrontano quando si confrontano con la potenza e la flessibilità di awk
.
Imparare awk a usare awk
Le basi di awk
sono sorprendentemente semplici. Si nota spesso che awk
è un linguaggio di programmazione e, sebbene sia relativamente elementare, è vero. Ciò significa che puoi imparare awk
nello stesso modo in cui impari un nuovo linguaggio di programmazione: impara la sua sintassi usando alcuni comandi di base, apprendi il suo vocabolario in modo da poter sviluppare azioni complesse, e poi esercitati, esercitati, esercitati .
Come awk analizza l'input
Awk
vede l'input, essenzialmente, come un array. Quando awk
esegue la scansione di un file di testo, tratta ogni riga, individualmente e in successione, come un record. Ogni record è suddiviso in campi. Naturalmente, awk
deve tenere traccia di queste informazioni e puoi vedere i dati utilizzando NR
(numero di record) e NF
(numero di campi) variabili integrate. Ad esempio, questo ti dà il conteggio delle righe di un file:
$ awk 'END { print NR;}' example.txt
36
Questo rivela anche qualcosa sulla sintassi di awk
. Sia che tu stia scrivendo awk
come un one-liner o come uno script autonomo, la struttura di un'istruzione awk
è:
pattern or keyword { actions }
In questo esempio, la parola END
è una parola chiave speciale e riservata anziché un modello. Una parola chiave simile è BEGIN
. Con entrambe queste parole chiave, awk
esegue semplicemente l'azione tra parentesi all'inizio o alla fine dell'analisi dei dati.
Puoi usare un modello come filtro o qualificatore in modo che awk
esegua una determinata azione solo quando è in grado di abbinare il tuo modello al record corrente. Ad esempio, supponiamo di voler utilizzare awk
, proprio come faresti con grep
, per trovare la parola Linux in un file di testo:
$ awk '/Linux/ { print $0; }' os.txt
OS: CentOS Linux (10.1.1.8)
OS: CentOS Linux (10.1.1.9)
OS: Red Hat Enterprise Linux (RHEL) (10.1.1.11)
OS: Elementary Linux (10.1.2.4)
OS: Elementary Linux (10.1.2.5)
OS: Elementary Linux (10.1.2.6)
Per awk
, ogni riga nel file è un record e ogni parola in un record è un campo. Per impostazione predefinita, i campi sono separati da uno spazio. Puoi cambiarlo con l'opzione --field-separator
, che imposta la variabile FS
(separatore di campo) su quello che vuoi che sia:
$ awk --field-separator ':' '/Linux/ { print $2; }' os.txt
CentOS Linux (10.1.1.8)
CentOS Linux (10.1.1.9)
Red Hat Enterprise Linux (RHEL) (10.1.1.11)
Elementary Linux (10.1.2.4)
Elementary Linux (10.1.2.5)
Elementary Linux (10.1.2.6)
In questo esempio è presente uno spazio vuoto prima di ogni elenco perché è presente uno spazio vuoto dopo ogni due punti (:
) nel testo di origine. Questo però non è cut
, quindi non è necessario che il separatore di campo sia limitato a un carattere:
$ awk --field-separator ': ' '/Linux/ { print $2; }' os.txt
CentOS Linux (10.1.1.8)
CentOS Linux (10.1.1.9)
Red Hat Enterprise Linux (RHEL) (10.1.1.11)
Elementary Linux (10.1.2.4)
Elementary Linux (10.1.2.5)
Elementary Linux (10.1.2.6)
Funzioni in awk
Puoi creare le tue funzioni in awk
usando questa sintassi:
name(parameters) { actions }
Le funzioni sono importanti perché ti consentono di scrivere il codice una volta e riutilizzarlo durante il tuo lavoro. Quando si costruiscono righe di una riga, le funzioni personalizzate sono un po' meno utili di quanto lo siano negli script, ma awk
definisce già molte funzioni per te. Funzionano sostanzialmente come qualsiasi altra funzione in qualsiasi altra lingua o foglio di calcolo: impari l'ordine in cui la funzione ha bisogno di informazioni da te e puoi alimentarla con ciò che desideri per ottenere i risultati.
Esistono funzioni per eseguire operazioni matematiche ed elaborazione di stringhe. Quelli matematici sono spesso abbastanza semplici. Fornisci un numero e lo scricchiola:
$ awk 'BEGIN { print sqrt(1764); }'
42
Le funzioni stringa possono essere più complesse ma sono ben documentate nel manuale GNU awk. Ad esempio, la funzione split
prende un'entità che awk
vede come un singolo campo e la divide in parti diverse. Richiede un campo, una variabile da utilizzare come array contenente ciascuna parte della divisione e il carattere che si desidera utilizzare come delimitatore.
Utilizzando l'output degli esempi precedenti, so che c'è un indirizzo IP alla fine di ogni record. In questo caso, posso inviare solo l'ultimo campo di un record alla funzione split
facendo riferimento alla variabile NF
perché contiene il numero di campi (e il campo finale deve essere il numero più alto):
$ awk --field-separator ': ' '/Linux/ { split($NF, IP, "."); print "subnet: " IP[3]; }' os.txt
subnet: 1
subnet: 1
subnet: 1
subnet: 2
subnet: 2
subnet: 2
Ci sono molte altre funzioni e non c'è motivo di limitarsi a una per blocco di codice awk
. Puoi costruire pipeline complesse con awk
nel tuo terminale, oppure puoi scrivere script awk
per definire e utilizzare le tue funzioni.
Scarica l'eBook
Imparare awk
è principalmente questione di usare awk
. Usalo anche se significa duplicare funzionalità che già possiedi con sed
o grep
o cut
o tr
o qualsiasi altro comandi perfettamente validi. Una volta che ti senti a tuo agio, puoi scrivere funzioni Bash che invocano i tuoi comandi awk
personalizzati per un utilizzo più semplice. E alla fine sarai in grado di scrivere script per analizzare set di dati complessi.
Scarica il nostro eBook per imparare tutto ciò che devi sapere su awk
, e inizia a usarlo oggi stesso.