Eigene Funktionen
Bisher haben wir hauptsächlich Funktionen verwendet, die PHP zur Verfügung stellen. In diesem Tutorial geht es nun darum, eigene Funktionen zu schreiben und zu verwenden.
Oftmals hat man beim Programmieren ein gewisses Problem, dass an mehreren Stellen auftritt, beispielsweise möchte man an mehreren Stellen seiner Scripte Werte einer gewissen mathematischen Funktion berechnen. Hier jedes mal den Code zu kopieren würde die Scripts stark aufblähen und den Programmcode außerdem noch schlecht wartbar machen. Muss man beispielsweise etwas am Code verändern, müsste man alle Stellen heraussuchen und die Änderung durchführen. Deswegen empfiehlt es sich, gewisse Funktionalitäten zu kapseln und als eigene Funktion zu definieren.
Inhaltsverzeichnis
Eigene Funktionen definieren
Nachfolgend ein kleines Beispiel. Angenommen wir haben zwei Zahlen $a und $b und falls $a+$b größer als $a*$b ist, wollen wir $a+$b ausgeben. Dies kann als Funktion wie folgt aussehen:
<?php function zusammenrechnen($a, $b) { $addition = $a+$b; $multiplikation = $a*$b; if($addition > $multiplikation) { return $addition; } else { return $multiplikation; } } echo zusammenrechnen(1,10)."<br />"; echo zusammenrechnen(2,3)."<br />"; echo zusammenrechnen(-5,8)."<br />"; ?>
Eine eigene Funktion startet mit dem Schlüsselwort function gefolgt von dem Namen der Funktion, in diesem Fall zusammenrechnen. Darauf folgen die verschiedenen Parameter der Funktion, die per Komma voneinander getrennt sind. Hier haben wir uns für die zwei Parameter $a und $b entschieden. Wir können mehr Parameter angeben oder auch gar keinen, je nach Aufgabe und Problem dass wir lösen möchten.
Danach folgt der Rumpf der Funktion. Dort berechnen wir erst das Ergebnis der Addition, dann das Ergebnis der Multiplikation der zwei Parameter. Falls das Ergebnis der Addition größer ist als das der Multiplikation, verwenden wir das Schlüsselwort return um einen Wert zurückzugeben. Mit return wird ein Wert oder eine Variable zurückgegeben und die Funktion wird nicht weiter ausgeführt.
Aufrufen können wir unsere Funktion ganz normal wie jede andere Funktion in PHP. Wir übergeben gewisse Werte oder Variablen die Werte enthalten und bekommen das Ergebnis zurück.
Parameter einer Funktion
Wie im vorherigen Beispiel gezeigt, kann eine Funktion beliebige viele Parameter besitzen. Auf die Werte der Parameter können wir dann im Funktionsrumpf wie auf jede andere Variable zugreifen. Die Variablen sind nur innerhalb einer Funktion gültig, d.h. wenn ihr Variablen innerhalb einem Funktionsrumpf ändert, dann hat dies keine Auswirkung auf andere Variablen (ausgenommen sind globale Variablen wie beispielsweise $_SESSION).
Hier ein kurzes Beispiel:
<?php $name = "Klaus"; echo "Hallo, mein Name ist $name"; function meineFunktion($neuer_name) { if(strlen($neuer_name) < 3) { echo "Neuer Name zu kurz"; } else { $name = $neuer_name; echo "In der Funktion heißt du $name"; } } meineFunktion("Petra"); echo "Der Wert von der Variable name ist: $name"; ?>
Dass Variablen nur die Gültigkeit innerhalb des Rumpfs besitzen hat einen guten Grund. So verhindert ihr, dass eine Funktion irgendwelche Werte in eurem Script abändert, ohne dass ihr das wollt. Auf der anderen Seite bedeutet dies aber auch, dass ihr alle Variablen als Parameter übergeben müsst, die ihr in der Funktion verwenden wollt.
Folgendes Beispiel funktioniert nicht:
<?php $wochentag = "Sonntag"; function begruessung($name) { echo "Hallo $name, ich wünsche dir einen schönen $wochentag"; } begruessung("John"); ?>
Die korrekte Variante hiervor ist:
<?php $wochentag = "Sonntag"; function begruessung($name, $tag_in_der_woche) { echo "Hallo $name, ich wünsche dir einen schönen $tag_in_der_woche"; } begruessung("John", $wochentag); ?>
Im letzteren Beispiel haben wir uns entschieden, den Parameter $tag_in_der_woche zu nennen. Man hätte diesen auch $wochentag nennen können oder irgendeine andere gültige Bezeichnung, das wäre egal. Innerhalb des Funktionsrumpfs können wir also nur Variablen verwenden die wir entweder als Parameter der Funktion definiert haben ($name, $tag_in_der_woche), oder die wir im Funktionsrumpf definiert haben
Optionale Parameter für Funktionen
Oft möchte man nicht unbedingt für alle Parameter einer Funktion einen Wert übergeben, sondern es soll ein gewisser default Wert angenommen werden. Dies können wir recht einfach in PHP umsetzen, indem wir den Standardwert hinter einem Gleichheitszeichen nach dem Parameter schreiben:
<?php function zeilenumbrueche_ersetzen($text, $neues_zeichen = "<br />") { return str_replace("\n", $neues_zeichen, $text); } $text = "Dies \n ist \n ein \n Beispiel \n\n"; echo zeilenumbrueche_ersetzen($text); echo zeilenumbrueche_ersetzen($text, " --UMBRUCH --"); ?>
Die Funktion im obigen Beispiel hat zwei Parameter, einmal den Parameter $text der immer gesetzt sein muss. Und noch den Parameter $neues_zeichen. Falls für diesen kein Wert angeben wurde, wird als Wert <br /> angenommen.
Nun können wir die Funktion mit einem Parameter aufrufen und nur $text übergeben, oder wir nutzen beide Parameter. Default Werte könnt ihr für alle Parameter einer Funktion setzen, was allerdings nicht funktioniert, erst einen Pflichtparameter zu setzen, dann einen optionalen Parameter und dann noch einen Pflichtparameter. Das heißt, ihr müsst erst alle Pflichtparameter definieren und könnt erst dann die optionalen Parameter definieren.
Wenn ihr eine Funktion mit default Werten für Parameter aufruft, müsst ihr auch die Reihenfolge der Parameter beachten. Es geht beispielsweise nicht, für den ersten Parameter den default Wert zu verwenden, für den zweiten dann aber einen setzen zu wollen. Siehe folgendes Beispiel:
<?php function meine_funktion($parameter1 = "Eins", $parameter2="Zwei", $parameter3="Drei") { echo "Parameter1: $parameter1 <br />"; echo "Parameter2: $parameter2 <br />"; echo "Parameter2: $parameter3 <br />"; } echo meine_funktion(); echo meine_funktion("Argument1"); echo meine_funktion("Argument1", "Argument2"); echo meine_funktion("Argument1", "Argument2", "Argument3"); ?>
Angenommen ihr wollt die obige Funktion aufrufen und nur einen Wert für $parameter3 setzen. Dies geht leider nicht, ihr müsst zuvor auch Werte für $parameter1 und $parameter2 setzen. Deswegen ist es sinnvoll, eine gewisse Reihenfolge in den Parametern zu haben, d.h. die Parameter die man wohl am häufigsten benutzt als erstes zu definieren und die, die man am seltensten benutzt, als letztes zu definieren.
Rückgabewerte von Funktionen
Funktionen können Werte mit dem Befehl return zurückgegeben werden. Der Gebrauch von dem Befehl ist optional, das heißt, eine Funktion kann einen Wert zurück geben, muss aber keinen. In unserem initialem Beispiel haben der Funktion zusammenrechnen() haben wir den Gebrauch von return bereits gesehen. Wichtig ist zu bedenken, dass die Funktion nicht weiter ausgeführt wird, sobald wir return ausführen. Das folgende Beispiel veranschaulicht dieses:
<?php function rechnen($a, $b) { if($a == 0 or $b == 0) { return null; } echo "Berechne Ergebnis für $a und $b:"; return 10.0/$a + 100.0/$b; } echo rechnen(10,2); echo rechnen(0,10); echo rechnen(5,2); ?>
Falls einer der Parameter den Wert 0 hat, wird ein null zurückgegeben. Ansonsten wird per echo eine Ausgabe generiert und es wird ein Wert berechnet und zurückgegeben.
Mehrere Variablen zurückgeben
Mit return können wir einen Wert zurückgeben. Manchmal möchten wir aber mehr Werte zurückgeben, beispielsweise wollen wir in einem Text ein gewisses Wort suchen und ersetzen und ebenfalls wollen wir wissen, wie oft es ersetzt wurde. Um dies zu erreichen, gibt man die verschiedenen Variablen typischerweise in einem Array zurück. Das folgende Beispiel veranschaulicht dieses:
<?php function suchen_und_ersetzen($text, $suche, $ersetzen) { $anzahl = substr_count($text, $suche); $neuer_text = str_replace($suche, $ersetzen, $text); return array($anzahl, $neuer_text); } $text = "Dies ist ein Beispiel und es ist ein ziehmlich einfaches Beispiel"; $ergebnis = suchen_und_ersetzen($text, "ist", "war"); echo "Anzahl: ".$ergebnis[0]."<br />"; echo "Neuer Text: ".$ergebnis[1]; ?>
Zuerst ermitteln wir per substr_count($text, $suche) wie oft $suche in $text vorkommt. Danach nutzen wir str_replace($suche, $ersetzen, $text) um alle Vorkommen zu ersetzen. Beide Ergebnis, also die Anzahl der Vorkommen und den neuen Text, geben wir als Array zurück. Auf das einzelnen Ergebnisse können wir dann über die Indices [0] zugreifen für die Anzahl und [1] für die Häufigkeit.
Sofern wir viele Werte zurückgeben wollen, dann kann die Nummerierung der Ergebnisse schnell verwirrend werden. Es empfiehlt sich dann auf assoziative Arrays zurück zu greifen:
<?php function suchen_und_ersetzen($text, $suche, $ersetzen) { $anzahl = substr_count($text, $suche); $neuer_text = str_replace($suche, $ersetzen, $text); return array("anzahl" => $anzahl, "neuer_text" => $neuer_text); } $text = "Dies ist ein Beispiel und es ist ein ziehmlich einfaches Beispiel"; $ergebnis = suchen_und_ersetzen($text, "ist", "war"); echo "Anzahl: ".$ergebnis['anzahl']."<br />"; echo "Neuer Text: ".$ergebnis['neuer_text']; ?>
Tipps für einen sauberen Programmierstile
Zum Abschluss des Tutorials noch ein paar Tipps für einen sauberen Programmierstile bzgl. Funktionen:
- Eine Aufgabe pro Funktion - Eure Funktionen sollten nicht versuchen alle Aufgaben auf einmal zu lösen. Stattdessen macht es Sinn, pro Funktion nur eine Aufgabe zu lösen. Wenn ihr komplexer Aufgaben untergliedern könnt in kleinere Aufgaben, dann macht es Sinn dafür eigene Funktionen zu schreiben. Möchtet ihr Beispielsweise die Eingaben in einem Formular überprüfen und dann die Daten abspeichern, dann solltet ihr dies in mehreren Funktionen machen. Beispielsweise eine Funktion zum Überprüfen einzelner Felder, z.B. des E-Mail-Feldes, dann eine Funktion die überprüft das alle Felder korrekt ausgefüllt und schlussendlich eine Funktion zum Abspeichern des Formulars.
- Aussagekräftige Funktionsnamen wählen - Funktionsnamen wie a(), b() sind vielleicht kurz zu schreiben, aber sie sagen später wenig aus wenn ihr die Funktion in eurem Script aufruft. Wählt stattdessen aussagekräftige Funktionsnamen, so dass schon am Namen erkenntlich wird, was die Funktion macht. Falls ein aussagekräftiger Name zu lang wird ist dies vielleicht ein Hinweis, dass eure Funktion zu komplex ist und ihr diese lieber zerlegen solltet in unterschiedliche Funktionen?
- Keine echo-Ausgaben in Funktionen - Hier im Tutorial haben wir ab und zu Textausgaben per echo in den Funktionen gehabt. Dies ist allerdings schlechter Stile, denn später wenn ihr die Funktion aufruft könnt ihr nicht mehr beeinflussen ob ihr die Ausgabe haben wollt oder nicht. Stattdessen solltet ihr lieber mit returns arbeiten. Also statt einen Text per echo auszugeben, gebt diesen per return zurück und ihr seid später frei zu entscheiden, ob ihr den Text ausgeben wollt oder ob ihr den weiterverarbeiten wollt.
- Dokumentation der Funktion - Es empfiehlt sich, die Funktion kurz zu kommentieren. Schreibt dazu vor der Funktion einen Kommentar. Oftmals dokumentiert man kurz die Funktionalität, die Parameter und den Rückgabewert. Schreibt diese Dokumentation bevor ihr die Funktion schreibt, dies hilft euch einen klareren Stile zu haben.Eine gute und weit verbreitete Dokumentation kann wie folgt aussehen:
1234567891011<?php/*** Überprüft ob der Benutzer volljährig ist. Ist dies so, wird true zurück gegeben* @param string birthdate Geburtsdatum des Benutzers* @param int adulthood Ab wie vielen Jahren ist man volljährig, per default 18 Jahre* @return boolean true, wenn der Benutzer volljährig, sonst false*/function isAdult($birthdate, $adulthood=18) {//Hier steht meine Code}?>
Zuerst wird in dem Kommentar die grundlegende Funktion beschrieben. Gefolgt von den Parametern die wir mit dem Wort @param einleiten, gefolgt von dem Typ (z.B. String oder Int) und einer kurzen Beschreibung. Zuletzt steht der Rückgabewert den wir mit @return einleiten, gefolgt vom Typ des Rückgabewerts und erneut einer kurzen Beschreibung.Dies ist nur ein Beispiel wie ihr Funktionen kommentieren könnt, zwingend ist die Dokumentation nicht. Sie hilft euch aber, wenn ihr später nochmal auf den Code schaut.