Previous: Abstract Classes & Abstract Methods
Duck typing in Python is a programming concept where the type or the class of an object is less important than the methods it defines. When you use duck typing, you do not check types at all. Instead, you check for the presence of a given method or attribute.
“Let's think about a situation where we see a bird. The bird quacks, swims, and walks like a duck; we can call this bird a duck.”
When a method works with the objects, it only cares about what is the behavior and attribute of that object, without caring for the type of object (which class the object belongs). However, in Python you can check which class of an object (when the object is transmitted to the method/function as a parameter).
For example, we define a simple class Duck:
# Duck Typing with Python
class Duck:
def quack(self):
print("Quack!")
def walk(self):
print("Waddle waddle")
Now, define a subclass that has no inheritance from the above class:
# Duck Typing with Python
class Duck:
def __init__(self, name):
self.__name = name
@property
def name(self):
return self.__name
def quack(self):
print("Quack!")
def walk(self):
print("Waddle waddle")
# A simple subclass or even unrelated class
class Person:
def __init__(self, name):
self.__name = name
@property
def name(self):
return self.__name
def quack(self):
print("I'm pretending to be a duck!")
def main():
donald = Duck("Donald")
person = Person("James")
donald.quack()
person.quack()
main()
Output:
Quack!
I'm pretending to be a duck!
Optional: Define a function outside the class but use the class attribute.
# Duck Typing with Python
class Duck:
def __init__(self, name):
self.__name = name
@property
def name(self):
return self.__name
def quack(self):
print("Quack!")
def walk(self):
print("Waddle waddle")
def make_it_quack(duck):
duck.quack()
def main():
duck = Duck("Hammer")
make_it_quack(duck)
main()
Output:
Quack!
Optional: What is wrong with this code?
# Duck Typing with Python
class Duck:
def __init__(self, name):
self.__name = name
@property
def name(self):
return self.__name
def quack(self):
print("Quack!")
def walk(self):
print("Waddle waddle")
# A simple subclass or even unrelated class
class Person:
def __init__(self, name):
self.__name = name
@property
def name(self):
return self.__name
def main():
donald = Duck("Donald")
person = Person("James")
donald.quack()
person.quack()
main()