HomepageTeaching PageResearch PageResources Page

Homework: Dogs and Inheritance

Chapter 18 is all about modelling playing cards in Python. If you're interested in that, read sections 18.1 through 18.7 in the book, which set up and use inheritance. It's a bit long, so if that doesn't interest you, you can skip it. Don't skip the stuff below!

Create a Dog class. Add an __init__ method that doesn't do anything explicitly (pass). Add some other methods:

    def speak(self):
        """Prints the noise a dog makes."""
        print("Woof!")
        
    def has_tail(self):
        """Returns whether this dog has a tail."""
        return True
        
    def has_muzzle(self):
        """Returns whether this dog has a long snout."""
        return True
        

Test your code:

>>> pluto = Dog()
>>> pluto.speak()
Woof!
>>> pluto.has_tail()
True
>>> pluto.has_muzzle()
True
>>>
        

Let's add another class, Goof. Just as with Dog, the class header should be fully unindented in the editor. Unlike Dog, we're going to put something new inside the parentheses:

class Goof(Dog):
    """Represents a Goof object, e.g. Goofy.  (https://en.wikipedia.org/wiki/Goofy)"""
        

This time, don't add any method. Let's test the code one last time, with some surprising results:

>>> goofy = Goof()
>>> goofy.speak()
Woof!
>>> goofy.has_tail()
True
>>> goofy.has_muzzle()
True
>>>
        

Even though we didn't define these three methods in the Goof class, it has them anyways! This is because in the first line of the class, we declared that our new class inherits from the Dog class. That means that every Goof automatically has all the methods, fields, and class variables that Dog objects have. It inherits all of those class features. We say that Dog is the superclass of Goof, and Goof is the subclass of Dog.

For those of you familiar with Goofy, it's clear that he doesn't actually speak in this way (and he doesn't actually have a tail). We can override these things by re-defining them in the Goof subclass:

class Goof(Dog):
    """Represents a Goof object, e.g. Goofy.  (https://en.wikipedia.org/wiki/Goofy)"""
    
    def speak(self):
        print("Hyuk hyuk!")
        
    def has_tail(self):
        return False
        

One last check to see that everything works correctly:

>>> pluto = Dog()
>>> pluto.speak()
Woof!
>>> pluto.has_tail()
True
>>> pluto.has_muzzle()
True
>>> goofy = Goof()
>>> goofy.speak()
Hyuk hyuk!
>>> goofy.has_tail()
False
>>> goofy.has_muzzle()
True
>>>
        

Now Goof overrides the appropriate methods and inherits all the others!