Vererbung am Beispiel Pizza


Vererbung ist eine wichtige Programmiertechnik in der OOP (Objekt Orientierte Programmierung). Im Kapitel Mehrere Turtleobjekte wurde bereits erklärt, wie man Programme mit Turtle-Objekten schreibt. In diesem Kapitel werden weitere Programmiertechniken der OOP erklärt.

Bei einem "Pizza Kurier" können folgende Pizzas bestellt werden:

  Margarita: Tomaten, Mozzarella, Oregano
  Prosciutto: Tomaten, Mozzarella, Schinken
  Vegetariana: Tomaten, Mozzarella, Gemüse
  Napoli: Tomaten, Mozzarella, Schinken, Champignons, Oliven


Da alle Pizzasorten Teig, Tomaten und Mozzarella enthalten, ist es sinnvoll diese Aufgabe mit Hilfe von Klassen und Vererbung zu lösen. Die Pizzas werden als Softwareobjekte beschrieben unter Berücksichtigung der gemeinsamen Eigenschaften. Diese Programmiertechnik wird als objektorientierte Programmierung (OOP) bezeichnet und ist bei höheren Programmiersprachen wie z. Bsp. Java sehr verbreitet. Die Grundzutaten sind in der Basisklasse Pizza enthalten. Die übrigen Pizzas sind von der Klasse Pizza abgeleitet. Sie erben alle Zutaten der Basisklasse und haben zusätzlich aber noch weitere Zutaten.

Die Definition einer Klasse in Python beginnt mit dem Schlüsselwort class gefolgt von Klassennamen. Wird eine Klasse abgeleitet, so muss der Name der Basisklasse in einer Klammer angegeben werden. Abgeleitete Klassen erben alle Methoden der Basisklasse, man kann aber auch weitere Methoden hinzufügen oder die Methoden der Basisklasse überschreiben. Eine Methode unterscheidet sich von einer Funktion nur in zwei Aspekten:
- sie ist innerhalb einer Klassen-Definition definiert
- der erste Parameter einer Methode ist immer self

Die Basisklasse Pizza hat Methoden drawDoutgh(), drawTomato(), drawMozarella(), createPizza() und displayPrice(). Die Programme für die einzelnen Pizzasorten sind danach sehr einfach, da nur die Darstellung von speziellen Zutaten beschrieben werden müssen.

Pizza Napoli kann von der Pizza Prosciutto abgeleitet werden, da sie die gleichen Zutaten und zusätzlich noch Pilze und Oliven hat.

In der Applikationsklasse "PizzaKurier" wird in einem Inputdialog nach der gewünschten Pizza gefragt. Danach wird mit createPizza() die richtige Pizza dargestellt und ihr Preis angezeigt.

 

# Pizza.py

from gturtle import *
from math import *

class Pizza():
    def drawDough(self): 
        setPenColor(makeColor(255, 218, 148))
        setPos(0, 0)
        dot(400) 

    def drawTomato(self): 
        setPenColor(makeColor(200, 50, 0))
        dot(350) 
  
    def drawMozzarella(self): 
        setPenColor(makeColor(243, 243, 210))
        for i in range(6):
            setPos(sin(i * pi/3) * 140, cos(i * pi/3) * 140)
            dot(50) 
            
    def createPizza(self): 
        self.drawDough()
        self.drawTomato()
        self.drawMozzarella() 

    def displayPrice(self): 
       setPenColor("blue")
       setPos(-300, -250)
       label(" Please pay  " + str(self.getPrice()) + "0 Fr.")
       
Programmcode markieren (Ctrl+C kopieren, Ctrl+V einfügen)


# Margarita.py

from gturtle import *
import random
from pizza import Pizza
       
class Margarita(Pizza):
    def drawIngredients(self):
        setPenColor(makeColor(23, 67, 0))
        for i in range(70):
            setPos(random.random()*200-100, random.random()*200-100)
            dot(10)  

    def getPrice(self):
        return 15.50
    
Programmcode markieren (Ctrl+C kopieren, Ctrl+V einfügen)


# Prosciutto.py

from gturtle import *
from pizza import Pizza
         
class Prosciutto(Pizza):
    def drawIngredients(self):
        setPenColor(makeColor(171, 87, 84))
        setPos(0, 0)
        dot(220)

    def getPrice(self):
        return 19.50
Programmcode markieren (Ctrl+C kopieren, Ctrl+V einfügen)


# Vegetariana.py

from gturtle import *
from pizza import Pizza
           
class Vegetariana(Pizza):
    def drawIngredients(self):
        setPenColor(makeColor(65, 116, 65))
        setPos(0, 0)
        dot(220)

    def getPrice(self):
        return 18.00
Programmcode markieren (Ctrl+C kopieren, Ctrl+V einfügen)


# Napoli.py

from gturtle import *
from math import *
from prosciutto import Prosciutto
           
class Napoli(Prosciutto):
    def drawIngredients(self):
        Prosciutto.drawIngredients(self)
        self.addFungi() 
        self.addOlives()
                 
    def addFungi(self):
        setPenColor(makeColor(190, 190, 190))
        setPos(0, 0)
        dot(100)
  
    def addOlives(self): 
        setPenColor("black")
        for i in range(1, 5):
            setPos(sin(i * pi/2) * 85, cos(i * pi/2) * 85)
            dot(25)
            
    def getPrice(self):
        return 22.50
Programmcode markieren (Ctrl+C kopieren, Ctrl+V einfügen)


# Pizzakurier.py

from gturtle import *
from margarita import Margarita
from prosciutto import Prosciutto
from vegetariana import Vegetariana
from napoli import Napoli

choice = inputString("Margarita, Prosciutto, Vegetariana or Napoli?")
myPizza = None
if choice == "Margarita": 
    myPizza = Margarita()
elif choice == "Prosciutto":
    myPizza = Prosciutto()
elif choice == "Vegetariana": 
    myPizza = Vegetariana()
elif choice == "Napoli": 
    myPizza = Napoli()  
else:
    msgDlg("No pizza of this type!") 
               
if myPizza != None:
    makeTurtle()
    hideTurtle() 
    myPizza.createPizza()
    myPizza.drawIngredients()
    myPizza.displayPrice()
    setTitle(choice)
Programmcode markieren (Ctrl+C kopieren, Ctrl+V einfügen)

 

Erklärungen zum Programmcode:

Die Methoden createPizza(), drawIngredients() und displayPrice() erhalten erst zur Laufzeit die Information, welche Pizza gewählt wurde. Ein solches Binden von Methoden-Aufrufen, bei dem eine Methode zur Laufzeit dynamisch, passend zum tatsächlich verwendeten Objekt, gewählt wird, bezeichnet man in der OOP als Polymorphismus.
Alle Programme müssen im gleichen Unterverzeichnis gespeichert werden. Sie können die Programmcodes zum Pizza-Beispiel auch hier herunterladen.
Weitere Beispiele zum objektorientierten Programmieren finden Sie im Kapitel Spielprogrammierung

 


Aufgabe: Serie 19

  Beim Mc Donald können verschiedene Burger bestellt werden: Hamburger, Cheesburger, Veggiburger, Chickenburgern BigMac usw. Versuche diese mit Hilfe der Vererbung darzustellen, indem du zuerst einer Basisklasse Burger mit den Methoden drawBred(), drawFilling(), createBurger() und getPrice() schreibst. Vielleicht gelingt es dir die verschiedenen Hamburgersorten noch schöner zu zeichnen...


  Analog zum PizzaKurier-Beispiel soll zu Beginn eine Dialogbox erscheinen, in der nach dem gewünschtern Burger gefragt wird.