Practical Extraction and Report Language


Perl ist eine interpretierte Sprache, die für die Erschließung, Aufbereitung und Neuformatierung beliebiger Textdateien optimiert ist. Perl ist auch für viele Systemverwaltungsarbeiten geeignet. Perl kann C, sed, awk und sh ersetzen und überwindet alle Beschränkungen der diese Sprachen unterliegen.

Dieser Text enthält eine kurze Darstellung der wichtigsten Perl Sprachkonstrukte und ihre Verwendung. Der Inhalt ist wie folgt:

Inhalt

  1. Einleitung
  2. Sprachkonstrukte
  3. CGI Beispiel

Einleitung

Perl wurde von Lary Wall entwickelt, die aktuelle Version ist 5.0. Eine andere Umschreibung von Perl lautet Pathologically Eclectic Rubbish Lister.

Perl Programme stehen in der Regel in Dateien mit der Endung .pl. Diese Programme, die auch oft Perl Skripten genannt werden, können mit

perl tuwas.pl

ausgeführt werden. Unter UNIX Systemen ist noch eine andere Variante üblich. Falls die erste Zeile des Skripts enthält Namen des Perl Interpreters enthält, wird dieser als Shell benutzt um des Skript auszuführen.

#!/usr/bin/perl

# ist der übliche Unix Kommentar, ! in der ersten Zeile bedeutet, daß der Name eins Kommandointerpreters folgt. /usr/bin/ ist eine Pfadangabe, die angibt wo Perl zu finden ist. Auf anderen Rechnersystemen wie Unix gibt es ähnliche Mechanismen. Z.B. unter OS/2 würde in einer .cmd Datei in der ersten Zeile extproc perl -Sx und in der zweiten Zeile dann #! perl stehen.

Als ein kurzes einleitendes Beispiel betrachten wir das folgende Program; es fragt nach dem Namen und gibt dann "Hallo, ... !" aus.


      (1)  #!perl
      (2)  print "Wie ist dein Name ? ";
      (3)  $name = <STDIN>;
      (4)  chop($name);
      (5)  print "Hallo, $name !\n";

Die erste Zeile (1) haben wir schon kennengelernt. In der Zeile (2) und (5) sehen wir das print Statement. Ein Zeilenvorschub muß wie unter C mit Hilfe von eingebetteten Kontrollsequenzen erzeugt werden (hier \n für Newline). Zeichenketten, die in " eingeschlossen sind werden interpoliert, d.h. vorkommende Variablen (hier $name) werden substituiert bevor die Zeichenkette weiter verwendet wird. Variablen müssen nicht vor der Benutzung deklariert werden, allerdings muß ihr Name immer mit $ beginnen.

In der Zeile (3) wird der Variablen $name mit = ein Wert zugewiesen. Dieser Wert stammt in unseren Fall aus der Datei STDIN. Dateien werden durch sogenannte Filehandles (in < > eingeschlossene Dateinamen) angesprochen. <STDIN> liefert eine Zeichenkette, die aus der nächsten Zeile der Datei besteht. Ein erneuter Aufruf von <STDIN> liefert dann die nächste noch nicht gelesene Zeile. Da in dieser Zeichenkette noch das Zeichen für den Zeilenvorschub enthalten ist wird dieser in der Zeile (4) mit chop($name) entfernt.


Sprachkonstrukte

Wie in anderen Programiersprachen auch gibt es Zahlen und Zeichenketten (Literale). Zeichenketten gibt es in 2 Formen, mit einfachen Anführungsstrichen 'quoted strings' und mit doppelten Anführungsstrichen "interpolated strings". In interpolierten Zeichenketten werden Variablen substituiert und Kontrollsequenzen wie in printf von C ausgewertet. Die anderen Zeichenketten werden nicht verändert.

Für Zahlen gibt es die üblichen arithmetischen Operatoren (+ - * / % ** == != ). Die Operatoren für Zeichenketten sind z.B. . eq ne lt gt le ge. Mit Hilfe dieser Operatoren können beliebige Ausdrücke gebildet werden.

Bei der Verwendung der Literale und Variablen in Perl ist folgende Eigenheit gegenüber anderen Programmiersprachen zu beachten der Kontext in dem ein Literal oder eine Variable verwendet wird, wird durch die verwendeten Operatoren erzwungen. D.h. nicht die Datentypen der Variablen und Literale spezifizieren den Kontext, sondern verschiedene Operatoren. Betrachten wir zum Beispiel die Ausdrücke

      "33" + "45" 
       33  . 44

Im ersten Fall wird durch + eine Addition von Zahlen verlangt, "33" und "44" werden also in Zahlen konvertiert (33, 44) und dann zu 77 addiert.
Im zweiten Fall wird durch . eine Verkettung von Zeichenketten verlangt, 33 und 44 werden also in Zeichenketten konvertiert ('33', '44') und dann zu '3344' verkettet.

Variablen

Variablen brauchen wie schon gesagt nicht deklariert zu werden, aber ihre Namen müssen mit $ beginnen. Der Zuweisungsoperator für alle arten von Varaiblen ist =. Zum Beispiel $a = 55 weist der Variablen $a den Wert 55 zu.

Neben diesen einfachen Variablen, die skalare Variablen genannt werden, gibt es noch Variablen für normale und assoziative Arrays.

Die Namen normaler Array Variablen müssen mit @ beginnen, die Namen von Variablen für assoziative Arrays müssen mit % beginnen. Zum Beispiel

      @fred = (11,22,33);
      @barney = @fred;

definiert 2 Array Variablen @fred und @barney und weist ihnen den Wert (11,22,33) zu. D.h. die Arrays bestehen aus jeweils 3 Elementen mit den Werten 11, 22 und 33.

Die Indizes von normalen Arrays sind ganze Zahlen (bzw. Ausdücke, die sich zu ganzen Zahlen auswerten) wärend die Indizes von assoziativen Arrays beliebige Werte sein können. Zum Beispiel

      %fred = (1,22,'h',33,"\t",44);
      %barney = %fred;

definiert 2 Variablen für assoziative Arrays %fred und %barney und weist ihnen den Wert (1,22,'h',33,"\t",44) zu. Diese Werte sind so aufzufassen, daß 1, 'h' und "\t" Indizes bedeuten, und die Werte des assoziativen Arrays für die jeweiligen Indexwerte sind 22, 33 und 44.

So wie Operatoren den Kontext spezifizieren, wird durch die Verwendung von $, @ und % der Kontext Skalar, Array oder assoziatives Array spezifiziert. Damit sind wir vorbereitet, die Zugriffe auf die Variablen zu besprechen.

       $b = $a + $fred[2] + $fred{'h'};    

In diesem Beispiel erzwingt $ jeweils den Skalar-Kontext (so wie + den arithmetischen Kontext erzwingt). $a referenziert eine einfache Skalar Variable, $fred[2] referenziert das 2. Element einer Array Variablen im skalaren Kontext (also 22 im obigen Beispiel) und $fred{'h'} referenziert das Element mit Index 'h' eines assozativen Arrays im skalaren Kontext (also 33 im obigen Beispiel). Also bekommt $b mit den obigen Werten den Wert 55 + 22 + 33 also 110.

An diese Variablen können Zuweisungen stattfinden, wobei dann die Werte der entsprechenden Elemente modifiziert werden.

       $fred[2] = 222; 
       $fred{'h'} = 333;    

Die Variablen können auch in ihrem angestammten Kontext verwendet werden.

       @barney = (@fred,44); 
       @barney = %fred; 
       @barney = ( keys(%fred), values(%fred) );    

       %barney = (@fred,44); 

Das erste Statement weist das Array (11,222,33,44) dem Array @barney zu. Das zweite Statement weist das Array (1,22,'h',333,"\t",44) dem Array @barney zu. Das dritte Statement weist das Array (1,'h',"\t",22,333,44) dem Array @barney zu. Die Operatoren keys bzw. values liefern ein Array aller Indizes bzw. aller Werte eines assoziativen Arrays.
Das vierte Statement weist das Array (11,222,33,44) dem assoziativen Array %barney zu, d.h. keys( %barney ) ergibt (11, 33) und values( %barney ) ergibt (222, 44).

Soviel zu Variablen in Perl, weitere Informationen können dem Perl Handbuch entnommen werden.

Kontrollstrukturen

Statements sind die schon bekannten Zuweisungen VAR = EXPR; sowie Folgen von Statements { ... } (im folgenden als BLOCK bezeichnet). Statements müssen immer mit Semikolon abgeschlossen werden. Kontrollstatements sind - neben vielen anderen - die folgenden.

Nach der Auswertung der Ausdrücke EXPR bedeuten die leere Zeichenkette "", "0" und 0 false; alle anderen Werte bedeuten true (z.B. auch "00").

Match-Operatoren und Variablen Substitutionen.

Ein- und Ausgabe

Dateien, Pipes und Filehandles.

Print-Formatierung

Neben den genannten Sprachkonstrukten verfügt Perl über eine endlose Liste von Funktionen. Die Funktionen reichen von arithmetischen Funktionen und Funktionen für Zeichenketten bis zu Datenbank, Netzwerk und Interprozesskomunikations Funktionen.

Für weitere Informationen müssen wir auf die Perl Manual-Page und Perl Bücher verweisen.


CGI Beispiel

In diesem Abschnitt besprechen wir ein Perl Skript, das mit CGI zusammenarbeitet. Es dekodiert die von GCI empfangenen Variablen und Werte, generiert eine HTML Seite mit diesen Informationen und schickt sie an den Absender zurück.
#!/usr/bin/perl
# test perl program to be used for parsing CGI methods
# send anything to this script either via GET or POST methods

&InsertHeader("CGI generated text");
&Parse;
&InsertTrailer;

# subrountines
sub Parse {
    local(@pairs,$pair,$val,$pos, $i);

    if ($ENV{'REQUEST_METHOD'} eq "GET") {
        $in = $ENV{'QUERY_STRING'};
	print "Submitted via GET<P>\n";
    }
    elsif ($ENV{'REQUEST_METHOD'} eq "POST") {
        read(STDIN, $in, $ENV{'CONTENT_LENGTH'}+1);
	print "Submitted via POST<P>\n";
    }

    $i = 0;
    @pairs = split(/&/, $in);

    foreach $pair (@pairs) {
# do the special character conversion
	$pair =~ tr/+/ /;
	$pair =~ s/%(..)/pack("c",hex($1))/ge;

	$pos = index($pair,"=");
	$name = substr($pair,0,$pos);
	$val = substr($pair,$pos+1);

	$i++;
	$entry{$name} = $val;

	print "$i: entry\{\"$name\"\} = $entry{$name}<BR>\n";
    }

    return 1;
}

sub InsertHeader {
    local ($htmltitle) = @_;
    print "Content-type: text/html\n\n";
    print "<HTML>\n<HEAD>\n<TITLE> $htmltitle </TITLE>\n</HEAD>\n";
    print "<BODY>\n";
  
    return 1;
}

sub InsertTrailer {
    print "</BODY>\n";

    return 1;
}

&InsertHeader; bezeichnet eine Funktion, die einen korrekten HTML Header erzeugt. &InsertTrailer; erzeugt den letzten Teil der HTML Seite. &Parse; zerlegt die CGI-Parameter wie im Abschnitt zu CGI besprochen.