Python Funktionen

Willemers Informatik-Ecke


Bestellen bei Amazon
2015-07-31

Diese Seiten sind Grundlage meines Python-Buchs aus den ersten Recherchen.

Funktionen ermöglichen es, aus mehreren Befehlen einen neuen Befehl zusammenzusetzen und diesem einen eigenen Namen zu geben. Eine Funktion kann dann von beliebiger Stelle des Codes aufgerufen werden. Nach Abarbeitung der Befehle kehrt der Interpreter zu der Stelle zurück, wo er herkam. Die Absprungstelle merkt sich der Interpreter in einer Stapelstruktur. Der englische Begriff dafür lautet stack.

Definition einer Funktion

Unter Python wird eine selbstgeschriebene Funktion immer mit dem Schlüsselwort def eingeleitet. Es folgt der Name, unter dem die Funktion später aufgerufen wird und dann ein Klammerpaar. Den Abschluss der Zeile bildet ein Doppelpunkt, der wie bei Bedingungen und Schleifen mindestens eine eingerückte Zeile einfordert.
def zaehleBis10():
   for i in range(1,11,1):
       print(i)

zaehleBis10()
zaehleBis10()
Die Funktion zaehleBis10() enthält eine Schleife, die die Zahlen von 1 bis 10 auf dem Bildschirm ausgibt. Die Definition der Funktion bewirkt keine Aktivität des Programms. Erst wenn die Funktion aufgerufen wird, wird sie aktiv. Zur Demonstration passiert dies anschließend zweimal.

Beim Aufruf einer Funktion ist es wichtig, dass Sie die beiden Klammern nicht vergessen. Ohne diese enthält der Name der Funktion nur die interne Speicheradresse der Funktion. Diese allerdings könnten Sie einer Variablen zuweisen. Da nun diese Variable auch die Adresse der Funktion kennt, können Sie die Funktion auch über die Variable aufrufen. Im Augenblick scheint das eher Quatsch zu sein, aber es gibt tatsächlich praktische Anwendungen dafür.

def zaehleBis10():
   for i in range(1,11,1):
       print(i)

anders = zaehleBis10
anders() # ruft die Funktion zaehleBis10

Parameter

Will man erreichen, dass die Zahl, bis zu der gezählt wird, vom Aufrufer angegeben werden kann, können Sie einen Parameter definieren. Dieser Parameter wird zwischen die Klammern gesetzt.
def zaehle(ende):
   for i in range(1,ende+1,1):
       print(i)

zaehle(3)
zaehle(5)
Der erste Aufruf der Funktion wird nun also bis 3 und der zweite bis 5 zählen. Die Funktion kann den Parameter ende wie eine Variable verwenden. Hier wird der Parameter als Variable ende an den Aufruf von range() weitergereicht, um das Ende frei gestalten zu können.

Parametertypen prüfen

Parameter können vom Aufrufer frei belegt werden. Dumm nur, wenn statt der erwarteten Zahl ein Text übergeben wird. Um Probleme zu verhindern, können Sie den Typ einer Variablen mit der Funktion type prüfen.
def zaehle(ende): 
    if type(neues_limit) in (float, int):
        for i in range(1, ende+1, 1):
            print(i)
    else:
        print("nix")

Vorbelegte Parameter

Sie können die Parameter einer Funktion bei der Definition vorbelegen. Alle vorbelegten Parameter müssen beim Aufruf nicht zwingend angegeben werden. Sie erhalten dann eben den vorbelegten Wert. Die Funktion zaehle() wird nun so verändert, dass der Schritt beim Zählen als weiterer Paramter angegeben werden kann. Ansonsten wird eine Schrittweite von 1 angenommen.
def zaehle(ende, schritt=1):
   for i in range(1,ende+schritt,schritt):
       print(i)

zaehle(3)
zaehle(5, 2)
Der erste Aufruf endet bei 3 und verwendet als Schrittweite 1, weil sie nicht explizit angegeben ist.

Parameter per Namen belegen

Python ermöglicht es dem Aufrufer, die Paramter nicht nur in der vorgegebenen Reihenfolge zu belegen, sondern über die Namen der Parametervariablen. Dazu wird in der Klammer des Funktionsaufruf eine Zuweisung des Wertes an den Parameternamen durchgeführt.
def zaehle(ende, schritt=1):
   for i in range(1,ende+schritt,schritt):
       print(i)

zaehle(ende=3)
zaehle(5, schritt=2)
zaehle(schritt=2, ende=6)
Da der Name angesprochen wird, kann die Reihenfolge der Parameter egal sein. Durch diese Aufrufmethode wird gleichzeitig dokumentiert, welche Parameter gemeint sind. Das ist bei mehreren Parametern durchaus hilfreich. Beispiel:
termin(12,5)
Ist der Termin nun am 12.5. oder nach amerikanischer Lesart am 5.12.? Die Nennung der Parameternamen bringt Klarheit.
termin(monat=12,tag=5)
Nun ist es auch egal, ob der Programmierer der Funktion termin den tag oder den monat als ersten Parameter verwendet hat.

Rückgabewert

Eine mathematische Funktion liefert immer einen Wert zurück. Das kann eine Funktion in Python auch. Dazu muss am Ende der Funktion lediglich ein Wert mit dem Befehl return zurückgegeben werden.
def summiere(ende):
   summe = 0
   for i in range(1,ende+1,1):
       summe += i
   return summe

Summe = summiere(10)
print(summiere(3))
Die Variable Summe wird durch den Rückgabewert der Funktion summiere() initialisiert.

Wird eine Funktion nicht mit return abgeschlossen, wird automatisch return None hinzugefügt.

Globale und lokale Variablen

Variablen, die innerhalb einer Funktion initialisiert werden, sind außerhalb der Funktion nicht zugreifbar. Darum bezeichnet man sie als lokale Variablen.

Wenn eine Funktion einer globalen Variablen einen Wert zuweisen will, dann entsteht ein Problem. Der Interpreter hält dies für das Anlegen einer lokalen Variablen. Die globale Variable bleibt unverändert.

summe = 0

def summiere(ende):
   summe = 0
   for i in range(1,ende+1,1):
       summe += i

summiere(10)
print(summe)   # Das Ergebnis ist 0!
Das ist grundsätzlich auch ganz gut so. Denn grundsätzlich sollten die Werte, die von der Funktion verändert werden, über den Befehl return zurückgegeben werden und nicht per Seiteneffekt auf globale Variablen.

Andererseits kann es Situationen geben, in denen Sie unbedingt eine Variable außerhalb der Funktion verändern müssen. In diesem Fall können Sie sich helfen, indem Sie die Variale explizit als global deklarieren.

summe = 0

def summiere(ende):
   global summe # Verwende die globale Variable!
   summe = 0
   for i in range(1,ende+1,1):
       summe += i

summiere(10)
print(summe)   # Das Ergebnis ist nun 55!
Parametervariablen sind ebenfalls lokale Variablen.

Rekursion

Rekursionen sind Funktionen, die sich selbst aufrufen. Dieses Werkzeug ist mächtig und in bestimmten Situationen unabdingbar.

Da die Funktion nach ihrem Ablauf immer zu dem Punkt zurückkehrt, wo sie aufgerufen wurde, ist es auch möglich, dass sich die Funktion selbst aufruft. Prinzipiell ist das mit einer Schleife vergleichbar. Und wie bei einer Schleife ist es auch bei der Rekursion wichtig, darauf zu achten, dass es eine saubere Abbruchbedingung gibt.

Als einfaches Beispiel soll die rekursive Funktion zählen, allerdings zunächst rückwärts.

def zaehleRekursiv(bis):     # rekursive Funktion
    if bis>0:                # Endebedingung der Rekursion
       print(bis)            # Aktion
       zaehleRekursiv(bis-1) # Selbstaufruf

zaehleRekursiv(3)
Die Funktion wird von außen mit dem Parameter 3 aufgerufen. Da dieser größer als 0 ist, wird er zunächst auf dem Bildschirm ausgegeben. Dann ruft sich die Funktion selbst auf und vermindert dabei den Zähler um 1. Die Funktion wird also mit 2 aufgerufen, gibt diese aus, ruft sich mit 1 auf, gibt diese aus und ruft sich schließlich mit 0 auf.

Nun aber wird die Abfrage verhindern, dass sich die Funktion selbst aufruft. Stattdessen tut sie nichts weiter und kehrt zu ihrem Selbstaufruf zurück. Dort ist die Variable bis noch 1. Da aber kein Befehl mehr folgt, läuft die Funktion wieder auf ihr Ende, springt zurück zum Selbstaufruf. Dies wiederholt sich, bis die Funktion zu ihrem ersten Aufruf zurückkehrt, der außerhalb der Funktion liegt.

Um nun von 1 bis 3 zu zählen, müssen Sie den print()-Aufruf nur hinter den Selbstaufruf stellen. Dann nämlich ruft sich die Funktion immer wieder selbst auf, bis die Variable bis 0 ist. Sie kehrt dann hinter den Selbstaufruf zurück. Dort ist bis dann 1 und wird per print() ausgegeben. Wieder läuft die Funktion auf ihr Ende, springt hinter den Selbstaufruf und gibt eine 2 aus.

def zaehleRekursiv(bis):     # rekursive Funktion
    if bis>0:                # Endebedingung der Rekursion
       zaehleRekursiv(bis-1) # Selbstaufruf
       print(bis)            # Aktion

zaehleRekursiv(3)
Sie werden zurecht darauf hinweisen, dass es viel einfacher ist, mit einer Schleife zu zählen. Dennoch sollten Sie sich die beiden Zählrekursionen genauer anschauen, bis Sie verstanden haben, warum sie so funktionieren.

Rekursionen können bestimmte Probleme und Datenstrukturen extrem gut bearbeiten. Ein typisches Beispiel ist das Durchlaufen von Baumstrukturen, wie es die Verzeichnisstruktur einer Festplatte darstellt.


Homepage (C) Copyright 2014, 2015 Arnold Willemer