Python 繼承與多型(Inheritance & Polymorphism) | Python
在 Python 的物件導向程式設計中,繼承(Inheritance) 與 多型(Polymorphism) 是兩個核心概念。繼承讓你能夠重用既有的程式碼,而多型讓不同類別的物件可以透過相同的介面來操作。本篇將帶你深入了解這兩個重要的 OOP 特性。
什麼是繼承?
繼承允許一個類別(子類別)繼承另一個類別(父類別)的屬性和方法。子類別會自動擁有父類別的所有功能,同時可以新增或修改自己的行為。
# 定義父類別
class Animal:
def __init__(self, name, age):
self.name = name
self.age = age
def introduce(self):
print(f"我是 {self.name},{self.age} 歲")
# 定義子類別,繼承自 Animal
class Dog(Animal):
def bark(self):
print(f"{self.name} 說:汪汪!")
# 建立子類別的實例
my_dog = Dog("Buddy", 3)
my_dog.introduce() # 輸出:我是 Buddy,3 歲(繼承自 Animal)
my_dog.bark() # 輸出:Buddy 說:汪汪!(Dog 自己的方法)
使用 super() 呼叫父類別
當子類別需要擴充父類別的 __init__ 方法時,使用 super() 來呼叫父類別的方法:
class Animal:
def __init__(self, name, age):
self.name = name
self.age = age
class Dog(Animal):
def __init__(self, name, age, breed):
super().__init__(name, age) # 呼叫父類別的 __init__
self.breed = breed # 新增子類別專屬屬性
def info(self):
print(f"{self.name} 是一隻 {self.age} 歲的 {self.breed}")
dog = Dog("Buddy", 3, "柴犬")
dog.info() # 輸出:Buddy 是一隻 3 歲的 柴犬
方法覆寫(Method Overriding)
子類別可以覆寫父類別的方法,提供自己的實作:
class Animal:
def speak(self):
print("(動物發出聲音)")
class Dog(Animal):
def speak(self):
print("汪汪!")
class Cat(Animal):
def speak(self):
print("喵喵!")
# 每個子類別有自己的 speak 實作
dog = Dog()
cat = Cat()
dog.speak() # 輸出:汪汪!
cat.speak() # 輸出:喵喵!
多重繼承
Python 支援多重繼承(Multiple Inheritance),一個類別可以同時繼承多個父類別:
class Flyable:
def fly(self):
print(f"{self.name} 正在飛行")
class Swimmable:
def swim(self):
print(f"{self.name} 正在游泳")
class Duck(Animal, Flyable, Swimmable):
def speak(self):
print("嘎嘎!")
duck = Duck("Donald", 2)
duck.speak() # 輸出:嘎嘎!
duck.fly() # 輸出:Donald 正在飛行
duck.swim() # 輸出:Donald 正在游泳
使用多重繼承時要注意方法解析順序(MRO),Python 會按照特定的順序來查找方法。
多型(Polymorphism)
多型的核心概念是:不同類別的物件可以透過相同的介面(方法名稱)來操作,但各自有不同的行為:
class Dog:
def speak(self):
return "汪汪!"
class Cat:
def speak(self):
return "喵喵!"
class Bird:
def speak(self):
return "啾啾!"
# 多型:用同一個函式處理不同類別的物件
def animal_sound(animal):
print(animal.speak())
animals = [Dog(), Cat(), Bird()]
for animal in animals:
animal_sound(animal)
# 輸出:
# 汪汪!
# 喵喵!
# 啾啾!
鴨子型別(Duck Typing)
Python 採用 鴨子型別(Duck Typing) 的哲學:「如果它走起來像鴨子、叫起來像鴨子,那它就是鴨子。」也就是說,Python 不在乎物件的類別,只在乎它是否具有所需的方法:
class Robot:
def speak(self):
return "嗶嗶嗶!"
# Robot 不是 Animal 的子類別,但一樣可以使用
robot = Robot()
animal_sound(robot) # 輸出:嗶嗶嗶!
使用 isinstance() 檢查型別
isinstance() 可以檢查一個物件是否為特定類別或其子類別的實例:
dog = Dog()
print(isinstance(dog, Dog)) # 輸出:True
print(isinstance(dog, Animal)) # 輸出:True(Dog 繼承自 Animal)
print(isinstance(dog, Cat)) # 輸出:False
總結
繼承 讓你能夠建立類別之間的父子關係,重用並擴充既有的程式碼。 多型 則讓不同類別的物件能透過相同的介面來操作,搭配 Python 的鴨子型別特性,讓程式碼更加靈活。善用這兩個概念,能讓你的程式結構更加清晰且易於維護。希望這篇文章能幫助你更深入理解 Python 物件導向的精髓。
繼承與多型是物件導向的進階概念,建議先閱讀 Python 的物件導向程式設計。若想學習如何用裝飾器為類別方法增添功能,可以參考 Python 裝飾器(Decorators)入門教學。