Perl/Funktionen für die Kontrolle des laufenden Scripts

Aus SELFHTML-Wiki
Wechseln zu: Navigation, Suche

Inhaltsverzeichnis

[Bearbeiten] Allgemeines zu diesen Funktionen

Die hier versammelten Funktionen dienen vor allem dazu, bestimmte Dinge für das Script festzulegen, zu kontrollieren oder den Ablauf des Scripts zu beeinflussen. So kann eine Subroutine beispielsweise ermitteln, von wo aus sie aufgerufen wurde. Für eine Variable kann überprüft werden, ob sie einen Wert besitzt oder nicht. Die Gültigkeit (Lebensdauer) von Variablen kann auf bestimmte Bereiche des Scripts begrenzt werden. Scripts können in Fehlerfällen oder kritischen Situationen abgebrochen werden oder Warnungen ausgeben.

[Bearbeiten] caller - Aufrufkontext ermitteln

Ermittelt, von wo aus der aktuelle Programmteil aufgerufen wurde, und aus welchem Kontext heraus.

Erwartet als Parameter:
1. (optional) die Rückverfolgungstiefe als Zahl. Wenn Sie mit diesem Parameter experimentieren wollen, probieren Sie zunächst, den Wert 1 zu übergeben. Höhere Werte können dazu führen, dass weniger Information ermittelt wird als erhofft.

Gibt wahlweise einen Skalar oder eine Liste zurück. Wenn der Rückgabewert nur in einem Skalar gespeichert wird, enthält dieser nach Aufruf der Funktion den Namen des aufrufenden Packages. Welche weiteren Rückgabewerte in einer Liste gespeichert werden, zeigt das folgende Beispiel.

Beispiel
#!/usr/bin/perl -w
 
use strict;
use CGI::Carp qw(fatalsToBrowser);
 
print "Content-type: text/html\n\n";
print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
print "<html><head><title>Test-Ausgabe</title></head><body>\n";
my $Infos = Aufrufe_Starten();
print "$Infos\n";
print "</body></html>\n";
 
sub Aufrufe_Starten {
  my $Info_Einfach = Aufruf_Info_Einfach();
  my $A_S = "<h3>Einfache Aufruf-Infos:</h3><p>".$Info_Einfach."</p>";
  my $Info_Ausfuehrlich = Aufruf_Info_Ausfuehrlich();
  $A_S = $A_S."<h3>Ausführliche Aufruf-Infos:</h3><p>".$Info_Ausfuehrlich."</p>";
  return($A_S);
}
 
sub Aufruf_Info_Einfach {
   (my $Package, my $Datei, my $Zeile) = caller();
   my $A_I_E = "<strong>Aufruf erfolgte aus Package:</strong> ".$Package."<br>" if (defined $Package);
   $A_I_E = $A_I_E."<strong>Aufruf erfolgte aus Datei:</strong> ".$Datei."<br>" if (defined $Datei);
   $A_I_E = $A_I_E."<strong>Aufruf erfolgte aus Programmzeile:</strong> ".$Zeile if (defined $Zeile);
   return($A_I_E);
}
 
sub Aufruf_Info_Ausfuehrlich {
   (my $Package, my $Datei, my $Zeile, my $Subroutine, my $HasArgs, my $WantArray, my $EvalText, my $IsRequire) = caller(1);
   my $A_I_A = "<strong>Aufruf erfolgte aus Package:</strong> ".$Package."<br>" if (defined $Package);
   $A_I_A = $A_I_A."<strong>Aufruf erfolgte aus Datei:</strong> ".$Datei."<br>" if (defined $Datei);
   $A_I_A = $A_I_A."<strong>Aufruf erfolgte aus Programmzeile:</strong> ".$Zeile."<br>" if (defined $Zeile);
   $A_I_A = $A_I_A."<strong>Aufruf erfolgte aus Subroutine:</strong> ".$Subroutine."<br>" if (defined $Subroutine);
   $A_I_A = $A_I_A."<strong>HasArgs:</strong> ".$HasArgs."<br>" if (defined $HasArgs);
   $A_I_A = $A_I_A."<strong>WantArray:</strong> ".$WantArray."<br>" if (defined $WantArray);
   $A_I_A = $A_I_A."<strong>EvalText:</strong> ".$EvalText."<br>" if (defined $EvalText);
   $A_I_A = $A_I_A."<strong>IsRequire:</strong> ".$IsRequire."<br>" if (defined $IsRequire);
   return($A_I_A);
}
Das Beispiel gibt HTML-Code aus. Während der HTML-Ausgabe wird die Subroutine Aufrufe_Starten() aufgerufen. Der Rückgabewert des Aufrufs wird in dem Skalar $Infos gespeichert und anschließend ausgegeben.

Die Subroutine Aufrufe_Starten() ruft ihrerseits wieder die Subroutinen Aufruf_Info_Einfach() und Aufruf_Info_Ausfuehrlich() auf. Aus den Rückgabewerten dieser beiden Routinen wird eine Zeichenkette namens $A_S zusammengesetzt und zurückgegeben.
In Aufruf_Info_Einfach steht die einfache Variante eines typischen Aufrufs von caller. Dabei werden drei Listenelemente als Rückgabewert erwartet: der Name des aufrufenden Packages, der aufrufenden Perl-Datei, und die Nummer der Programmzeile, in der der Aufruf erfolgte.
Die Subroutine Aufruf_Info_Ausfuehrlich zeigt dagegen den erweiterten Aufruf von caller. Dabei werden acht Listenelemente als Rückgabewerte erwartet. Neben den drei Elementen der einfachen Variante sind das der Name der aufrufenden Subroutine und folgende Zusatzinformationen:
$HasArgs ist 1, wenn beim Aufruf Argumente übergeben wurden (dazu zählt auch eine leere Liste), ansonsten 0.
$WantArray speichert, ob die Funktion im Listenkontext aufgerufen wurde.
$EvalText speichert einen Inhalt, wenn der Aufruf aus einer eval()-Bewertung heraus erfolgt (jedoch nicht unbedingt bei Blockbewertungen mit eval{...}).
$IsRequire speichert 1 als Inhalt, wenn der Aufruf aus eval heraus erfolgte, und wenn dabei eine der Funktionen use oder require im Spiel sind.

Die beiden Subroutinen Aufruf_Info_Einfach und Aufruf_Info_Ausfuehrlich im obigen Beispiel stellen aus den gewonnenen Informationen die Zeichenketten $A_I_E bzw. $A_I_A zusammen und geben diese am Ende zurück.

[Bearbeiten] defined - Definition einer Variablen überprüfen

Variablen, egal, ob Skalare, Listen- bzw. Array-Elemente oder Hash-Elemente, haben, solange ihnen nicht explizit irgendein Wert zugewiesen wird, den Wert undef. Mit dieser Funktion können Sie überprüfen, ob einer Variablen bereits ein Wert zugewiesen wurde oder nicht.

Erwartet als Parameter:
1. die zu überprüfende Variable.

Gibt 1 bzw. ein logisches "wahr" zurück, wenn der Variablen ein Wert zugewiesen ist, und 0 bzw. ein logisches "falsch", wenn kein Wert zugewiesen ist.

Beispiel
#!/usr/bin/perl -w
 
use strict;
use CGI::Carp qw(fatalsToBrowser);
 
my $ErsterSatz;
my $ZweiterSatz = "Den ersten beissen die Katzen";
 
print "Content-type: text/html\n\n";
print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
print "<html><head><title>Test-Ausgabe</title></head><body>\n";
&Satz_aufsagen;
$ErsterSatz = "...und den letzten wie bekannt die Hunde";
undef $ZweiterSatz;
print "<p></p><i>So - und jetzt noch einmal:</i></p>";
&Satz_aufsagen;
print "</body></html>\n";
 
sub Satz_aufsagen {
  if(defined $ErsterSatz) {
    print "Der erste Satz lautet <strong>$ErsterSatz</strong><br>\n";
  }
  if(defined $ZweiterSatz) {
    print "Der zweite Satz lautet <strong>$ZweiterSatz</strong><br>\n";
  }
}
Das Beispielscript definiert zunächst zwei Skalare namens $ErsterSatz ohne Wertzuweisung und $ZweiterSatz mit Wertzuweisung. Das Script enthält eine Subroutine namens Satz_aufsagen. Darin wird mit defined für die beiden Skalare überprüft, ob ihnen ein Wert zugewiesen wurde. Wenn ja, wird dieser Wert ausgegeben.

Das Script erzeugt HTML-Code und ruft dabei zunächst einmal die Subroutine Satz_aufsagen auf. Anschließend erhält der bislang undefinierte Skalar $ErsterSatz einen Wert, und der Skalar $ZweiterSatz wird mit undef in jenen Zustand versetzt, in dem ihm kein Wert (bzw. der "Nichtwert" undef) zugewiesen ist. Danach wird Satz_aufsagen nochmals aufgerufen.

Beim ersten Aufruf von Satz_aufsagen wird nur "Den ersten beissen die Katzen" ausgegeben, beim zweiten Aufruf nur "...und den letzten wie bekannt die Hunde".
Beachten Sie: Der Anfangswert undef einer Variablen, den Sie mit der Funktion undef wieder herstellen können, ist etwas anderes als der so genannte Leerstring (""). Eine leere Zeichenkette ist durchaus ein zugewiesener Wert!

[Bearbeiten] die - Script wegen eines Fehlers abbrechen

Beendet ein Script, wenn es keinen Sinn hat, das Script weiter auszuführen. Wird z.B. gern verwendet, wenn eine wichtige Datei nicht geöffnet werden kann.
Schreibt Fehlermeldungen auf die Standardfehlerausgabe STDERR und beendet das Script mit dem aktuellen Wert der vordefinierten Variablen $!. Bei der CGI-Schnittstelle eines Webervers ist die Standardfehlerausgabe meistens eine Log-Datei, in der solche Fehlermeldungen gesammelt werden. Suchen Sie gegebenenfalls in der Dokumentation zu Ihrem Webserver nach, wo und wie der Server CGI-Fehlermeldungen protokolliert.

Erwartet als Parameter:
1. Eine Liste, die auf die Standardfehlerausgabe STDERR geschrieben werden soll. Sinnvollerweise enthält die Liste eine oder mehrere entsprechende Fehlermeldungen.

Beispiel
#!/usr/bin/perl -w
 
use strict;
use CGI::Carp qw(fatalsToBrowser);
 
open(TEXT, "<", "/daten/texte/nichtda.txt")
      or die "Fehler aufgetreten: $!";
my @Zeilen = <TEXT>;
close(TEXT);
Das Beispiel versucht, mit open eine Datei zu öffnen, die aber nicht vorhanden ist. Dadurch wird der Oder-Zweig hinter dem logischen Operator || (steht für "oder") aktiv. Dort ist die Funktion die notiert. Sie schreibt auf die Standardfehlerausgabe, dass ein Fehler aufgetreten ist. Indem sie dabei auch die vordefinierte Variable $! mit in die Ausgabe schreibt, wird auch mitprotokolliert, welcher Fehler aufgetreten ist. In diesem Fall ist auch die Anweisung use CGI::Carp qw(fatalsToBrowser) sehr hilfreich, denn der Fehler wird dadurch zusätzlich auf die Standardausgabe geschrieben und kann so je nach Situation im Browser zur Anzeige gelangen.

[Bearbeiten] eval - Anweisungen oder Anweisungsblöcke interpretieren lassen

Perl-Scripts werden normalerweise intern zu Operationscode (sogenannten Opcodes) kompiliert, bevor sie ausgeführt werden. Das merken Sie als Programmierer beispielsweise daran, dass der Perl-Interpreter vor der Ausführung abbricht, sobald das Script Syntaxfehler enthält. Mit Hilfe der eval-Funktion können Sie jedoch den Perl-Interpreter während der Laufzeit eines Scripts aufrufen und innerhalb des Scripts beliebigen Perl-Code interpretieren lassen. Wenn Sie so wollen, kann ein Perl-Script auf diese Weise selber Perl-Scripts schreiben und deren Ausführung in die eigene Ausführung einbetten. In die Code-Erzeugung dürfen natürlich auch Variableninhalte einfließen, die das Script verwaltet.

Erwartet als Parameter:
1. entweder eine Zeichenkette, die Perl-Code enthält, oder einen Anweisungsblock in geschweiften Klammern, vergleichbar einem Anweisungsblock innerhalb einer Subroutine oder innerhalb einer if-Abfrage.
Der Unterschied zwischen beiden Möglichkeiten besteht darin, dass eine übergebene Zeichenkette tatsächlich erst zur Laufzeit kompiliert wird, während der Anweisungsblock in der internen Vorab-Kompilierung mit berücksichtigt wird. Dadurch werden beispielsweise schwere Fehler, die zum Scriptabbruch führen, in einem übergebenen Anweisungsblock bereits bei der Kompilierung erkannt, in einer übergebenen Zeichenkette jedoch erst während der Ausführung.

Gibt das Ergebnis der zuletzt ausgeführten Anweisung in der übergebenen Zeichenkette oder dem übergebenen Anweisungsblock zurück. Im Fehlerfall wird undef zurückgegeben, und die aufgetretene Fehlermeldung ist über die vordefinierte Variable $@ abfragbar.

Beispiel
#!/usr/bin/perl -w
 
use strict;
use CGI::Carp qw(fatalsToBrowser);
 
my $Rechenergebnis = eval($ENV{'QUERY_STRING'});
 
print "Content-type: text/html\n\n";
print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
print "<html><head><title>Test-Ausgabe</title></head><body>\n";
print "Das Ergebnis der übergebenen Rechenoperation lautet <strong>$Rechenergebnis</strong><br>\n";
print "</body></html>\n";
Das Script erwartet beim Aufruf einen Übergabeparameter, der über URI hinter einem Fragezeichen notiert wird. Der Übergabeparameter besteht in einer Rechenoperation. Es kann sich auch um geklammerte, komplexe Rechenausdrücke handeln, z.B. ((6+7)*4)+(5/7). Nur Leerzeichen sind bei diesem einfachen Beispielscript nicht erlaubt, da sie bei der Übergabe in der URI-Zeile umformatiert werden.

Über die CGI-Umgebungsvariable $ENV{'QUERY_STRING'} kann das Script auf die übergebene Rechenoperation zugreifen. Es übergibt die Umgebungsvariable gleich an die Funktion eval. Die wiederum übergibt die übergebene Zeichenkette, also die Rechenoperation, zur Laufzeit an den Perl-Interpreter. Zurückgegeben wird der Wert dieser Anweisung, und das ist in dem Fall einfach das Rechenergebnis, so wie Perl es in einem Skalar speichern würde, wenn man ihm diese Rechenoperation zuweisen würde.

Zur Kontrolle gibt das Script HTML-Code mit dem Rechenergebnis aus.
Beachten Sie: Scripts wie im Beispiel oben können extrem gefährlich sein. Benutzen Sie so etwas niemals als öffentlich zugängliches CGI-Script! Denn der übergebene Code, den das Script vom Anwender erhält, wird gnadenlos ausgeführt. Wenn der Anwender jemand ist, der sich auskennt, kann er statt der geforderten Rechenoperation beispielsweise einen Aufruf von system übergeben, bei dem ein ganzer Verzeichnisbaum gelöscht oder die Festplatte formatiert wird.
Beispiel
#!/usr/bin/perl -w
 
use strict;
use CGI::Carp qw(fatalsToBrowser);
 
my $Zahl_1 = int(rand(50));
my $Zahl_2 = int(rand(5));
my $Ergebnis;
eval { $Ergebnis = $Zahl_1 / $Zahl_2; };
 
print "Content-type: text/html\n\n";
print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
print "<html><head><title>Test-Ausgabe</title></head><body>\n";
 
if($@) {
  print "Folgender Fehler ist aufgetreten: $@\n";
}
else {
  print "$Zahl_1 geteilt durch $Zahl_2 ist $Ergebnis\n";
}
print "</body></html>\n";
In diesem Beispiel wird die Funktion eval wie in der Praxis oft üblich zum Abfangen von Fehlern verwendet. Das Script ermittelt mit rand zwei Zufallszahlen $Zahl_1 und $Zahl_2. Anschließend dividiert es Zahl 1 durch Zahl 2. Da bei den ermittelten Zufallszahlen jedoch auch der Wert 0 vorkommen kann, würde ein schwerer Fehler auftreten, wenn Zahl 2 diesen Wert hat. Denn eine Division durch 0 führt auf allen Computersystemen zu einem Fehler. Das Script bettet die Anweisung mit der Division aus diesem Grund in einen eval-Block ein. Falls die Zahl 2 tatsächlich den Wert 0 hat, wird abgebrochen, und in der vordefinierten Variablen $@ steht anschließend die von Perl erzeugte Fehlermeldung.
Das Beispiel gibt HTML-Code aus. Dabei fragt es ab, ob $@ einen Inhalt enthält. Wenn ja, wird der Fehler ausgegeben. Wenn nein, wird das Ergebnis der erfolgreichen Division ausgegeben.

[Bearbeiten] exit - Script beenden

Beendet das Script und gibt einen Wert an den aufrufenden Prozess zurück.

Erwartet als Parameter:
1. (optional) einen zurückzugebenden Wert. Die üblichen Werte, die auch von fremden aufrufenden Prozessen am ehesten erkannt werden, sind 0 für "erfolgreich beenden" und 1 für "Beenden mit Fehler". Wenn Sie keinen Parameter übergeben, wird automatisch 0 verwendet.

Beispiel
#!/usr/bin/perl -w
 
use strict;
use CGI::Carp qw(fatalsToBrowser);
 
if($ENV{'QUERY_STRING'} eq "") {
   HTML_Output("Username beim Aufruf erwartet!");
   exit(1);
}
else {
   HTML_Output("Hallo $ENV{'QUERY_STRING'}, wie geht's?");
   exit(0);
}
 
sub HTML_Output {
  print "Content-type: text/html\n\n";
  print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
  print "<html><head><title>Test-Ausgabe</title></head><body>\n";
  print "$_[0]\n";
  print "</body></html>\n";
}
Das Script erwartet beim Aufruf einen Übergabeparameter, der hinter einem an den URI angehängten Fragezeichen notiert wird. Der Übergabeparameter besteht in einem User-Namen. Durch Auswerten der CGI-Umgebungsvariablen $ENV{'QUERY_STRING'} gelangt das Script an den übergebenen Namen. Wenn die Umgebungsvariable leer ist (""), wurde kein Name übergeben. In diesem Fall ruft das Script die Subroutine HTML_Output auf und lässt sie eine Fehlermeldung senden. Anschließend wird das Script mit exit(1) beendet. Im anderen Fall, wenn alles in Ordnung ist und ein Name übergeben wurde, ruft das Script ebenfalls HTML_Output auf, diesmal jedoch mit einer netten Begrüßung des Users. In diesem Fall beendet sich das Script anschließend mit exit(0).
Beachten Sie: Es ist kein guter Programmierstil, exit in Subroutinen zu verwenden. Wenn das Script in solchen Programmteilen fehlerhafte Situationen erkennt, sollte es besser mit return einen Wert zurückgeben, der an einer zentralen Stelle im Script als Fehler erkannt wird und dort zu einem Aufruf von exit führt.

[Bearbeiten] local - Wert von Variablen lokal begrenzen

Beschränkt den Wert einer Variablen (egal ob Skalar, Liste oder Hash usw.) auf lokale Gültigkeit. Die Beschränkung kann sich auf einen Anweisungsblock oder einen der Bereiche beziehen, die aus diesem Anweisungsblock heraus aufgerufen werden. Wenn es eine gleichnamige Variable außerhalb des Blocks gibt, wird dieser innerhalb des Anweisungsblocks temporär ein neuer Wert zugewiesen. Anwenden können Sie diese Funktion bei der Ersteinführung, also der Deklaration einer Variablen.

Beachten Sie, dass local nicht wirklich eine lokale Variable erzeugt, sondern nur eine globale Variable mit einem lokal gültigen Wert. Verwenden Sie local daher nur in begründeten Ausnahmefällen! "Echte" lokal gültige Variablen werden durch my deklariert.

Erwartet als Parameter:
1. eine Variable, der temporär ein neuer Wert zugewiesen werden soll.

Beispiel
#!/usr/bin/perl -w
 
use strict;
use CGI::Carp qw(fatalsToBrowser);
use vars qw($Zahl_1 $Zahl_2);
 
print "Content-type: text/html\n\n";
print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
print "<html><head><title>Test-Ausgabe</title></head><body>\n";
my $Ergebnis = Subroutine_1();
print $Ergebnis, "\n";
print "</body></html>\n";
 
sub Subroutine_1 {
   local $Zahl_1 = 10;
   $Zahl_1 = $Zahl_1 * 2;
   $Zahl_2 = Subroutine_2();
   return($Zahl_1 + $Zahl_2);
}
 
sub Subroutine_2 {
  return($Zahl_1 + 100);
 
}
Das Beispiel deklariert zu Beginn zwei Skalare $Zahl_1 und $Zahl_2. Dies sind globale Variablen, die überall Gültigkeit haben und an jeder Stelle des Scripts verändert werden können. Das Beispiel enthält weiter unten jedoch auch noch eine Subroutine namens Subroutine_1. Innerhalb dieser Subroutine, die aus Sicht von Perl einen Anweisungsblock darstellt, wird mit local $Zahl_1 einer dieser globalen Variablen für die Subroutine Subroutine_1 ein anderer Wert zugewiesen, nämlich 10. Würde das local fehlen, so würde einfach der globalen Variablen $Zahl_1 ein neuer Wert zugewiesen.

$Zahl_1 wird in der darauffolgenden Anweisung mit 2 multipliziert. Hinterher steht 20 als Wert in $Zahl_1, da die Multiplikation mit dem temporären Wert 10 vorgenommen wird.
Aus Subroutine_1 heraus wird anschließend Subroutine_2 aufgerufen. Dort wird wiederum die Variable $Zahl_1 verwendet. Zu diesem Zeitpunkt ist im Script-Ablauf der globale Wert 5 der Variablen $Zahl_1 noch immer durch den temporären Wert 20 ersetzt. Da er auch in Bereichen Gültigkeit hat, die von Subroutine_1 aus aufgerufen werden, wird dieser Wert innerhalb von Subroutine_2 weiter verwendet (hier liegt ein sichtbarer Unterschied zur Funktion my). Zum aktuellen Wert 20 wird 100 addiert. Der Wert, den Subroutine_2 mit return zurückgibt, lautet also 120.
Subroutine_1 gibt nach dem Aufruf von Subroutine_2 ebenfalls das Ergebnis einer Addition an den aufrufenden Befehl zurück. Da $Zahl_2 den Wert 120 hat, wird also der Wert 140 zurückgegeben.

Im Hauptprogramm erzeugt das Beispiel HTML-Code. Dabei wird Subroutine_1 aufgerufen und deren Rückgabewert im Skalar $Ergebnis gespeichert. Zur Kontrolle wird das Ergebnis ausgegeben.

[Bearbeiten] my - Gültigkeitsbereich von Variablen begrenzen

Schränkt den Gültigkeitsbereich einer Variablen (egal ob Skalar, Liste oder Hash usw.) auf einen Namensraum oder einen Anweisungsblock ein. Wenn es eine gleichnamige Variable außerhalb des Blocks gibt, wird diese nicht berührt. Anwenden können Sie diese Funktion bei der Definition einer Variablen.

Erwartet als Parameter:
1. eine Variable, deren Gültigkeitsbereich eingeschränkt werden soll.

Beispiel
#!/usr/bin/perl -w
 
use strict;
use CGI::Carp qw(fatalsToBrowser);
use vars qw($Zahl_1);
 
$Zahl_1 = 1;
 
print "Content-type: text/html\n\n";
print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
print "<html><head><title>Test-Ausgabe</title></head><body>\n";
my $Ergebnis = Subroutine_1();
print $Ergebnis, "\n";
print "</body></html>\n";
 
sub Subroutine_1 {
   my $Zahl_1 = 10;
   my $Zahl_2 = Subroutine_2();
   return($Zahl_1 + $Zahl_2);
}
 
sub Subroutine_2 {
 return($Zahl_1 + 100);
}
Das Beispiel deklariert zu Beginn einen Skalar $Zahl_1. Dies ist eine globale Variable, die überall Gültigkeit hat und an jeder Stelle des Scripts verändert werden kann. Die Deklaration erfolgt mit dem Standardmodul vars. Der Grund dafür ist, dass die Verwendung von use strict sonst keine Deklaration globaler Variablen erlaubt und einen Fehler erzeugen würde. Im Beispiel sehen Sie, wie das Modul vars eingesetzt wird. Mit use eingebunden, steht in der Klammer hinter qw der Name $Zahl_1, also der Name der Variablen, die global deklariert werden soll. In der Klammer hinter qw können Sie als Liste, durch Leerzeichen getrennt, auch mehrere globale Variablen angeben.

Das Beispielscript enthält weiter unten eine Subroutine namens Subroutine_1. Innerhalb dieser Subroutine, die aus Sicht von Perl einen Anweisungsblock darstellt, wird mit my $Zahl_1 eine Variable deklariert, die den gleichen Namen hat wie die globale Variable. Durch Anwendung von my ist es jedoch eine eigene neue Variable, die mit 10 initialisiert wird. Würde das my fehlen, so würde einfach der globalen Variablen $Zahl_1 ein neuer Wert zugewiesen.
Aus Subroutine_1 heraus wird Subroutine_2 aufgerufen. Dort wird wieder die Variable $Zahl_1 verwendet. Zu diesem Zeitpunkt im Script-Ablauf existieren beide Variablen $Zahl_1. Da diejenige, die in Subroutine_1 deklariert wurde, jedoch nur dort Gültigkeit hat, ist innerhalb von Subroutine_2 wieder die globale Variable gemeint. Zu deren Wert 1 wird 100 addiert. Der Wert, den Subroutine_2 mit return zurückgibt, lautet also 101.
Subroutine_1 gibt nach dem Aufruf von Subroutine_2 ebenfalls das Ergebnis einer Addition an den aufrufenden Befehl zurück. In diesem Fall ist mit $Zahl_1 wieder diejenige Variable gemeint, die innerhalb des gleichen Blocks, also innerhalb von Subroutine_1 deklariert wurde, und die den Wert 10 hat. Da $Zahl_2 den Wert 101 hat, wird also der Wert 111 zurückgegeben.

Im Hauptprogramm gibt das Beispiel HTML-Code aus. Dabei wird Subroutine_1 aufgerufen und deren Rückgabewert im Skalar $Ergebnis gespeichert. Zur Kontrolle wird das Ergebnis ausgegeben.

[Bearbeiten] quotemeta - Alle Zeichen außer A-Z, a-z, 0-9 und _ maskieren

Wandelt eine Zeichenkette so um, dass alle Zeichen außer A bis Z, a bis z, 0 bis 9 und Unterstrich _ mit einem Backslash \ maskiert werden.

Erwartet als Parameter:
1. eine Zeichenkette, die umgewandelt werden soll.

Gibt die umgewandelte Zeichenkette zurück.

Beispiel
#!/usr/bin/perl -w
 
use strict;
use CGI::Carp qw(fatalsToBrowser);
 
print "Content-type: text/html\n\n";
print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
print "<html><head><title>Test-Ausgabe</title></head><body>\n";
 
my $Normaltext = "+++Test+++";
my $Normallaenge = length($Normaltext);
my $Quotematatext = quotemeta($Normaltext);
my $Quotematalaenge = length($Quotematatext);
 
print "<strong>$Normaltext</strong> wurde umgewandelt in <strong>$Quotematatext</strong><br>\n";
print "Textlänge zuvor: <strong>$Normallaenge</strong> Zeichen<br>\n";
print "Textlänge jetzt: <strong>$Quotematalaenge</strong> Zeichen\n";
 
print "</body></html>\n";
Das Beispiel erzeugt HTML-Code. Dabei demonstriert es die Wirkungsweise von quotemeta. Ein Skalar namens $Normalext wird zunächst mit einem Wert belegt, der neben dem Wort "Test" diverse Pluszeichen enthält. Außerdem wird mit length die Länge der Zeichenkette ermittelt. Durch die anschließende Anwendung der Funktion quotemeta auf $Normaltext werden die Pluszeichen maskiert. Der Rückgabewert der Funktion wird in einem neuen Skalar namens $Quotemetatext gespeichert. Auch dessen Länge wird mit length ermittelt. Zur Kontrolle gibt das Script alle ermittelten Daten aus. Die maskierte Version hat 6 Zeichen mehr, da jedes Pluszeichen maskiert wurde.

[Bearbeiten] return - aus Subroutine zurückkehren und Wert zurückgeben

Gibt einen Wert an die Anweisung zurück, welche die Subroutine aufgerufen hat.

Erwartet als Parameter:
1. (optional) ein Wert, der zurückgegeben werden soll. Es kann sich um eine Zahl, eine Zeichenkette oder um eine beliebige Variable (auch um eine komplette Liste oder einen Hash) handeln. Wenn kein Parameter übergeben wird, wird einfach die Subroutine verlassen und je nach zuletzt ausgeführtem Kontext eine leere Liste oder ein Skalar mit dem Wert undef zurückgegeben.

Beispiel
#!/usr/bin/perl -w
 
use strict;
use CGI::Carp qw(fatalsToBrowser);
 
print "Content-type: text/html\n\n";
print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
print "<html><head><title>Test-Ausgabe</title></head><body>\n";
my $Ausgabe = fett("eine wichtige Angelegenheit");
print "<p>$Ausgabe</p>\n";
$Ausgabe = kursiv("eine noch wichtigere Angelegenheit");
$Ausgabe = fett($Ausgabe);
print "<p>$Ausgabe</p>\n";
print "</body></html>\n";
 
sub fett {
  my $fetterText = "<strong>" . ( $_[0] || '' ) . "</strong>";
  return $fetterText;
}
 
sub kursiv {
  my $kursiverText = "<i>" . ( $_[0] || '' ) . "</i>";
  return $kursiverText;
}
Das Beispiel enthält zwei Subroutinen namens fett und kursiv. In beiden Subroutinen wird ein übergebener Parameter erwartet, der in dem vordefinierten Array für Übergabeparameter (@_) an erster Stelle ($_[0]) steht. Dieser übergebene Parameter wird in die HTML-Tags für fett bzw. kursiv gesetzt. Die Skalare $fetterText bzw. $kursiverText, die dieses Konstrukt speichern, werden anschließend mit return zurückgegeben.
Das Script erzeugt HTML-Code. Während der Ausgabe ruft es die beiden Subroutinen auf. Der Rückgabewert wird jeweils in dem Skalar $Ausgabe gespeichert. Im zweiten Fall werden sogar beide Subroutinen hintereinander aufgerufen. Dadurch wird der übergebene Text erst kursiv, dann fett, also insgesamt fett kursiv. Zur Kontrolle werden die HTML-Konstrukte ausgegeben.
Beachten Sie: Subroutinen geben auch dann etwas zurück, wenn sie nicht mit return verlassen werden. Wenn Sie beispielsweise eine Subroutine so aufrufen:

$Ausgabe = Test();
und die Subroutine so aussieht:
sub Test { $x = 1; }

dann ist in $Ausgabe anschließend der Wert 1 gespeichert.

[Bearbeiten] scalar - Ausdruck in skalarem Kontext bewerten

Erwartet als Parameter:
1. einen beliebigen Ausdruck. Es kann sich um eine Variable, einen Funktionsaufruf, eine Berechnung, eine Zuweisung usw. handeln.

Gibt den Wert zurück, den der übergebene Ausdruck bei skalarem Kontext liefert.

Beispiel
#!/usr/bin/perl -w
 
use strict;
use CGI::Carp qw(fatalsToBrowser);
 
print "Content-type: text/html\n\n";
print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
print "<html><head><title>Test-Ausgabe</title></head><body>\n";
my $Singular = "ein Tisch";
my @Plural = ("ein Tisch","noch ein Tisch");
my $Ausgabe_1 = scalar($Singular);
my $Ausgabe_2 = scalar(@Plural);
my $Ausgabe_3 = scalar(time() > 900000000 ? 1 : 0);
print "Ausgabe 1: ", $Ausgabe_1, "<br>\n";
print "Ausgabe 2: ", $Ausgabe_2, "<br>\n";
print "Ausgabe 3: ", $Ausgabe_3, "\n";
print "</body></html>\n";
Das Beispiel gibt HTML-Code aus. Dabei definiert es einen Skalar namens $Singular und eine Liste namens @Plural. Auf beide wird die Funktion scalar angewendet. Der skalare Rückgabewert wird in den Skalaren $Ausgabe_1 und $Ausgabe_2 gespeichert. Außerdem wird noch ein dritter Skalar $Ausgabe_3 definiert, dem der skalare Kontext einer komplexeren Anweisung zurückgegeben wird. In der Anweisung wird ermittelt, ob der Rückgabewert der Funktion time größer als 900000000 ist. Wenn ja, wird 1 zurückgegeben, wenn nein, wird 0 zurückgegeben. Anschließend gibt das Script die 3 ermittelten Werte aus.

$Ausgabe_1 gibt einfach den Inhalt des Skalars $Singular aus, also ein Tisch. Da der bewertete Ausdruck ein Skalar ist, hat der skalare Kontext keinen Einfluss auf den zurückgegebenen Wert.
$Ausgabe_2 gibt eine Zahl aus, nämlich 2. Der Grund ist, dass die skalare Interpretation einer Liste, im Beispiel der Liste @Plural, die Anzahl der Elemente ermittelt, die in der Liste enthalten sind.

$Ausgabe_3 gibt 1 oder 0 aus, je nachdem, welchen Wert time zurückgeliefert hat. Da 1 und 0 normale Einzelwerte sind, ist der skalare Kontext bereits gegeben.

[Bearbeiten] wantarray - Überprüfen ob Listenkontext gegeben ist

Erwartet keine Parameter

Gibt 1 bzw. TRUE zurück, wenn das aufrufende Programm oder die aufrufende Subroutine einen Listenkontext erwartet, und 0 bzw. FALSE, wenn ein skalarer Kontext erwartet wird. Gibt undef zurück, wenn gar kein Kontext erwartet wird (sogenannter void context).

Beispiel
#!/usr/bin/perl -w
 
use strict;
use CGI::Carp qw(fatalsToBrowser);
 
print "Content-type: text/html\n\n";
print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
print "<html><head><title>Test-Ausgabe</title></head><body>\n";
 
my @Zahlen = (1,2,3,4,5);
 
my $Normalsumme = Summe_ermitteln(@Zahlen);
print "Die normale Summe von 1,2,3,4,5 ist <strong>", $Normalsumme, "</strong><br>\n";
 
my @Kumulativsummen = Summe_ermitteln(@Zahlen);
print "Die Kumulativsummen von 1,2,3,4,5 sind <strong>", @Kumulativsummen, "</strong><br>\n";
 
print "</body></html>\n";
 
sub Summe_ermitteln {
   if(wantarray) {
     my @Summe = @_;
     my $Wert;
     foreach my $Summe (@Summe) {
        $Summe = $Wert += $Summe;
     }
     return @Summe;
   }
   else {
     my $Wert;
     foreach my $Summe (@_) {
        $Wert += $Summe;
     }
     return $Wert;
   }
}
Das Beispiel enthält eine Subroutine namens Summe_ermitteln. Die Funktion erwartet einen Array von Zahlen als Parameter, die über die Parameterliste @_ abgefragt werden können. Innerhalb der Funktion wird mit if(wantarray) abgefragt, ob die Anweisung, die die Subroutine aufruft, als Rückgabewert eine Liste oder einen Skalar erwartet. Wenn eine Liste erwartet wird, wird der if-Zweig ausgeführt. Wenn ein Skalar erwartet wird, dann der else-Zweig. Im if-Zweig ist ein Algorithmus notiert, der aus den übergebenen Zahlen Kumulativsummen ermittelt. Die Kumulativsummen werden in einer Liste namens @Summe festgehalten. Diese Liste wird am Ende zurückgegeben. Im else-Zweig dagegen ermittelt die Funktion einfach nur die Summe der übergebenen Zahlen und hält das Ergebnis in dem Skalar $Wert fest, den sie am Ende zurückgibt.
Im Hauptprogramm wird HTML-Code erzeugt. Dabei wird insgesamt zweimal die Subroutine Summe_ermitteln aufgerufen. Einmal wird der Rückgabewert in einem Skalar namens $Normalsumme gespeichert, und beim anderen mal in einer Liste namens @Kumulativsummen. Dadurch wird beim ersten Aufruf der Subroutine der else-Zweig ausgeführt, und beim zweiten Aufruf der if-Zweig. Zur Kontrolle gibt das Script die jeweils ermittelten Ergebnisse aus.

[Bearbeiten] warn - Warnungen ausgeben

Schreibt Warnungen auf die Standardfehlerausgabe STDERR, ohne das Script zu beenden (im Gegensatz zu die). Für die CGI-Schnittstelle eines Webservers ist die Standardfehlerausgabe meistens eine Log-Datei, in der solche Fehlermeldungen gesammelt werden. Suchen Sie gegebenenfalls in der Dokumentation zu Ihrem Webserver nach, wo und wie der Server CGI-Fehlermeldungen protokolliert.

Erwartet als Parameter:
1. Eine Liste mit der oder den Meldungen, die auf die Standardfehlerausgabe STDERR geschrieben werden sollen.

Beispiel
#!/usr/bin/perl -w
 
use strict;
use CGI::Carp qw(fatalsToBrowser);
 
my $Daten = $ENV{'QUERY_STRING'};
 
print "Content-type: text/html\n\n";
print '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">', "\n";
print "<html><head><title>Test-Ausgabe</title></head><body>\n";
 
if(! -e "/tmp/idx.txt") {
  warn("idx.txt nicht gefunden. Datei wird deshalb neu erzeugt\n");
  open(FILE,">", "/tmp/idx.txt");
  print FILE "$Daten\n";
}
else {
  open(FILE,">>", "/tmp/idx.txt");
  print FILE "$Daten\n";
}
print "<strong>in Datei geschrieben:</strong> $Daten\n";
close(FILE);
 
print "</body></html>\n";
Das Script erwartet einen Übergabeparameter, der hinter einem Fragezeichen notiert wird. Der Übergabeparameter ist in diesem Beispiel ein User-Name. Durch Auswerten der CGI-Umgebungsvariablen $ENV{'QUERY_STRING'} gelangt das Script an die übergebenen Daten.

Das Script erzeugt HTML-Code. Währenddessen versucht es, mit open eine Datei namens /usr/web/temp/idx.txt zu öffnen, um die übergebenen Daten ans Ende der Datei zu schreiben. Falls die Datei nicht existiert, wird sie im if-Zweig zwar neu erzeugt (falls das Verzeichnis /usr/web/temp zumindest schon existiert), aber es wird mit warn eine entsprechende Warnung auf die Standardfehlerausgabe, die dem error_log des Webservers entspricht, geschrieben. Sie erhalten diese Warnung also nicht im Browserfenster angezeigt.
Zur Kontrolle wird auch noch übermittelt, welche Daten in die Datei geschrieben wurden. Diese Mitteilung sehen Sie allerdings in Ihrem Browser.

Die if-Abfrage überprüft mit dem Dateitestoperator -e, ob die Datei bereits existiert. Abhängig davon ist die Reaktion des Scripts.
Meine Werkzeuge
Namensräume

Varianten
Aktionen
Übersicht
Index
Mitmachen
Werkzeuge
Spenden
SELFHTML