-
regelbasierter Ansatz: AWK-Programme enthalten Folgen von Regeln, die aus
Mustern und Aktionen bestehen und der Reihe nach auf die Datensätze (meist
Zeilen) des Eingabe-Datenstromes angewendet werden
-
die Einlese-Schleife muss vom AWK-Anwender also nicht programmiert werden
-
AWK liest automatisch die als Argumente benannten Dateien oder, wenn diese
fehlen, die Standard-Eingabe
-
neben den Regeln kann ein Programm noch Funktions-Definitionen enthalten
-
AWK-Programme bestehen also prinzipiell aus einer Folge von Regeln und
Funktions-Definitionen:
pattern { action statements }
function name(parameter list) { statements }
-
Beispiel:
#include(summe_sp2.awk)
-
Aufruf-Beispiel:
#include(summe_sp2.sh)
-
das Muster oder die Aktion einer Regel kann fehlen:
- leeres Muster: Regel gilt für alle Datensätze
- leere Aktion: Ausgabe des aktuellen Datensatzes, also print
-
Aufbau der Muster:
BEGIN
END
/regular expression/
relational expression
pattern && pattern
pattern || pattern
pattern ? pattern : pattern
(pattern)
! pattern
pattern1, pattern2
-
jeder Datensatz wird automatisch in Felder zerlegt, auf die man bequem zugreifen kann,
z.B.
$1 --> Feld 1 des aktuellen Satzes
$NF --> letztes Feld des aktuellen Satzes
NF --> Anzahl der Felder des aktuellen Satzes (number of fields)
$0 --> die komplette Eingabezeile
-
Feld- und Datensatz-Trenner sind für Ein- und Ausgabe getrennt über spezielle
Variablen einstellbar:
- FS (field separator)
- OFS (output field separator)
- RS (record separator)
- ORS (output record separator)
-
Manipulationen an Feldern (Zuweisungen, Veränderung der Feld-Anzahl durch
Änderung von NF) führen zu einer Neuberechnung von
$0; dabei wird OFS als
Feld-Trenner benutzt
-
AWK-Programme sind im allg. recht kompakt, aber dennoch lesbar
-
sinnvolle AWK-Programme sind nicht selten "One-liners", also sehr kurze
Code-Stücke, die aus einer Zeile oder nur wenigen Zeilen bestehen
-
Beispiele:
#include(one_liners.sh)
-
Funktionsumfang von AWK ist fest definiert und überschaubar
-
Erweiterungen durch Module/externe Bibliotheken sind standardmäßig nicht
vorgesehen
Anmerkungen:
-
die Gawk-spezifische Funktion extension()
zum dynamischen Nachladen von Funktionen ist laut Handbuch ein experimentelles
Feature, dessen Nutzung im allgemeinen nicht empfohlen wird
-
das Shell-Skript igawk realisiert einen rein textuellen
Include-Mechanismus zum Einfügen von AWK-Dateien in andere AWK-Programme:
#include(igawk.awk)
-
auf Grund einer klugen Mittel-Auswahl ist AWK in seinem Einsatzgebiet dennoch
ausgesprochen flexibel
-
Integration regulärer Ausdrücke in die Sprache; aber weniger mächtig als bei
Perl und Co. (z.B. fehlen Lookahead und Lookbehind)
-
nur zwei skalare Datentypen: Strings und Gleitpunktzahlen
-
Gleitpunktzhalen sind bei modernen Implementierungen double-precision
floating-points
-
Achtung: die Locale (speziell der Dezimaltrenner der Locale) kann die Arbeit
von AWK beeinflussen:
#include(locale.sh)
-
AWK kennt daneben noch numerische Strings: das sind Strings, die wie (gültige)
Zahlen aussehen
-
dieses Konzept dient auch der Typ-Bestimmung von Variablen:
-
numerische Konstanten sowie Ergebnisse numerischer Operationen haben den Typ
NUMERIC
-
String-Konstanten sowie Ergebnisse von String-Operationen haben den Typ STRING
-
Felder, über getline() gelesene Eingaben, der
Inhalte der Spezial-Variablen FILENAME, die Elemente
der Felder ENVIRON und ARGV
sowie die durch die Funktion split() generierten
Feld-Elemente haben den Typ STRNUM, wenn ihre Werte
numerische Strings sind, andernfalls den Typ STRING
-
uninitialisierte Variablen haben auch den Typ STRNUM
-
Variablen werden bei Benutzung automatisch angelegt und im Falle einer
Zuweisung auch initialisiert
-
uninitialisierte Variablen haben je nach Kontext als impliziten Wert den leeren
String oder die Zahl Null
-
bei Zuweisungen des Inhalts einer Variablen an eine andere Variable
wird auch der Typ der Ausgangs-Variablen mit zugewiesen
-
der Variablen-Typ bestimmt, wie deren Werte verglichen werden:
numerisch oder als Strings
-
Vergleichs-Regeln:
| Typ | STRING | NUMERIC | STRNUM |
| STRING | String | String | String |
| NUMERIC | String | numerisch | numerisch |
| STRNUM | String | numerisch | numerisch |
-
Daten werden je nach Kontext automatisch von Strings in Zahlen und umgekehrt
konvertiert
Beispiel:
#include(konvert.awk)
-
im Booleschen Kontext (also bei Vergleichen) werden der leere String sowie die
Zahl 0 als FALSE und alle anderen Werte als TRUE interpretiert
-
zusätzlich zu skalaren Variablen existieren mehrdimensionale assoziative Arrays
(Hashes, Dictionaries) mit Strings als Schlüssel bzw. Index
-
die verschiedenen Indexe werden de facto zu einem String zusammengefügt, wobei
der Inhalt der Variablen SUBSEP als Trenner dient;
intern handelt es sich also immer um eindimensionale Arrays
-
einmal erzeugte skalare Variablen sind nachfolgend nur skalar und
Array-Variablen entsprechend nur als Array-Variablen nutzbar
-
Variablen sind standardmäßig global
-
überzählige Argumente benutzerdefinierter Funktionen sind lokal
Beispiel:
#include(lokale_vars.awk)
Aufruf-Möglichkeit:
#include(lokale_vars.sh)
-
automatisches Speicher-Management beim Anlegen von Variablen und Arrays sowie
beim Löschen von Feld-Inhalten mittels delete
-
Operatoren und Anweisungen sind an die Sprache C angelehnt; zusätzlich
existiert mit ^ bzw. ** der
Potenz-Operator