BEGIN e END con il comando awk

Secondo il manuale di awk, BEGIN e END non sono usati per abbinare linput, ma piuttosto per fornire avvio e pulizia -up informazioni allo script awk. Ecco lesempio fornito:

ls -l | \ awk "BEGIN { print "Files found:\n" } /\<[a|x].*\.conf$/ { print $9 }" Files found: amd.conf antivir.conf xcdroast.conf xinetd.conf 

Per prima cosa stampa una stringa in output. Quindi controlla linput per una corrispondenza del modello, in cui linput inizia con a o x seguito da qualsiasi carattere una o più volte seguito da .conf. Per ogni corrispondenza, viene stampata la nona colonna.

Il fatto che siamo costretti a usare inizia qui, significa che awk può usare solo al massimo una funzione di stampa che contiene un BEGIN o END? In caso contrario, perché non possiamo semplicemente utilizzare la funzione di stampa allinizio senza la parola chiave BEGIN? Sembra che BEGIN sia superfluo.

Commenti

  • La semplice esecuzione del comando senza BEGIN risponderebbe alla tua domanda, dimostrando che ' non è superfluo e che otterrai un risultato diverso.

Risposta

BEGIN non è superfluo. Se non specifichi BEGIN, print verrà eseguito per ogni riga di input.

Citando da il manuale :

A BEGIN la regola viene eseguita una sola volta, prima che il primo record di input venga letto. Allo stesso modo, una regola END viene eseguita una sola volta, dopo che tutto linput è stato letto.

$ seq 5 | awk "BEGIN{print "Hello"}/4/{print}" # Hello printed once Hello 4 $ seq 5 | awk "{print "Hello"}/4/{print}" # Hello printed for each line of input Hello Hello Hello Hello 4 Hello $ 

Risposta

awk elabora ogni riga di input per le espressioni fornite nel corpo diverse da BEGIN e END blocchi. Nel caso di BEGIN e END blocchi, awk elaborerà le istruzioni solo una volta, prima che sia iniziata lelaborazione dellinput e dopo che lelaborazione dellinput sia stata eseguita risp ectively. Senza il blocco BEGIN, non solo non saresti in grado di stampare informazioni una tantum come le intestazioni, ma non saresti in grado di inizializzare in modo efficiente alcune delle variabili richieste dal corpo. Inoltre, FYI, un programma awk può avere più blocchi BEGIN e END.

Answer

awk esegue ogni blocco solo quando il pattern prima di esso corrisponde. Il modello vuoto (solo blocco) corrisponde a ogni riga. BEGIN e END sono modelli speciali che corrispondono allinizio e alla fine del file (analogo al significato di ^ e $ in direzione orizzontale).

Se desideri eseguire qualcosa prima di leggere il file, utilizza BEGIN. Ad esempio, inizializzazione di contatori o qualcosa del genere. END potrebbe quindi raccogliere i risultati.

Risposta

Nellesempio fornito, il che credo sia semplificato per chiarezza pedagogica, hai ragione che è superfluo. È possibile ottenere gli stessi risultati senza utilizzare BEGIN.

1 == NR { print "Files found:\n" } /\<[a|x].*\.conf$/ { print $9 } 

produrrebbe gli stessi risultati poiché listruzione print è limitati solo alla prima riga di input.

Detto questo, i blocchi BEGIN e END sono incredibilmente potenti utensili. Come accennato in altre soluzioni, puoi utilizzare il blocco BEGIN per inizializzare variabili o altre routine che devono essere eseguite solo una volta ma può anche essere utilizzato per eseguire comandi Awk quando non ci sono file da elaborare. Un semplice esempio:

BEGIN { print sqrt(12/4) } 

Puoi vedere un esempio più serio di programmazione in Awk senza elaborare alcun input qui .

Allo stesso modo, il blocco END è estremamente utile per eseguire calcoli e riassumere tutto linput. Questo non può essere fatto (di solito) senza prima leggere tutti i dati. Un semplice esempio di riepilogo dellinput può essere trovato qui

Lascia un commento

Il tuo indirizzo email non sarà pubblicato. I campi obbligatori sono contrassegnati *