第17天:多型與抽象類別
課程簡介
多型(Polymorphism)和抽象類別是物件導向程式設計(OOP)的兩個核心概念。多型允許不同的類別通過相同的介面來執行不同的操作,使程式更具靈活性和可擴展性。抽象類別是定義了一組子類別必須實現的方法的類別,但不能直接實例化。今天我們將學習如何運用多型和抽象類別來設計靈活且可擴展的程式架構。
學習內容
1. 多型的基本概念
多型允許多個類別共享相同的介面,即使這些類別的具體實現不同。這意味著我們可以使用相同的方法來操作不同類別的物件,而不需要知道它們的具體類型。
範例:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
class Dog:
def speak(self):
return "Bark!"
class Cat:
def speak(self):
return "Meow!"
# 函數使用多型
def animal_speak(animal):
print(animal.speak())
# 創建物件
dog = Dog()
cat = Cat()
animal_speak(dog) # 輸出: Bark!
animal_speak(cat) # 輸出: Meow!
在這個範例中,Dog
和 Cat
類別都實現了 speak()
方法,animal_speak()
函數可以接受這兩種類別的物件並調用相應的方法,而不必關心物件的具體類型。
2. Python 中的多型
Python 中的多型是一種「鴨子類型」(duck typing),這是一個動態語言的特性,只要物件具有某個方法或屬性,它就可以被看作是某個特定的類型,而不必關心這個物件的實際類別。
範例:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
class Bird:
def fly(self):
print("Bird is flying.")
class Airplane:
def fly(self):
print("Airplane is flying.")
# 使用多型
def fly_thing(thing):
thing.fly()
bird = Bird()
airplane = Airplane()
fly_thing(bird) # 輸出: Bird is flying.
fly_thing(airplane) # 輸出: Airplane is flying.
3. 抽象類別的基本概念
抽象類別 是一個定義了方法但無法直接實例化的類別。它用來為子類別提供通用的介面,要求子類別實現具體的方法。Python 使用 abc
模組中的 ABC
和 abstractmethod
來定義抽象類別和抽象方法。
範例:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
from abc import ABC, abstractmethod
# 定義抽象類別
class Animal(ABC):
@abstractmethod
def speak(self):
pass
# 子類別必須實現抽象方法
class Dog(Animal):
def speak(self):
return "Bark!"
class Cat(Animal):
def speak(self):
return "Meow!"
dog = Dog()
print(dog.speak()) # 輸出: Bark!
# 無法直接實例化抽象類別
# animal = Animal() # 這會導致錯誤
在這個範例中,Animal
是一個抽象類別,定義了一個抽象方法 speak()
,所有繼承 Animal
的子類別必須實現這個方法。抽象類別無法被直接實例化,只能作為基礎類別提供統一的介面。
4. 抽象類別與多型的結合
抽象類別通常與多型結合使用。通過定義抽象類別,可以確保不同的子類別都實現了相同的介面,從而實現多型操作。
範例:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
from abc import ABC, abstractmethod
class Shape(ABC):
@abstractmethod
def area(self):
pass
class Circle(Shape):
def __init__(self, radius):
self.radius = radius
def area(self):
return 3.14 * self.radius ** 2
class Rectangle(Shape):
def __init__(self, width, height):
self.width = width
self.height = height
def area(self):
return self.width * self.height
# 多型函數
def print_area(shape):
print(f"The area is: {shape.area()}")
circle = Circle(5)
rectangle = Rectangle(4, 6)
print_area(circle) # 輸出: The area is: 78.5
print_area(rectangle) # 輸出: The area is: 24
這裡,Shape
是抽象類別,Circle
和 Rectangle
是其子類別。通過 print_area()
函數,我們可以使用多型來計算不同形狀的面積,而不必關心形狀的具體類型。
5. Python 中的介面(Interface)
在某些程式語言中,有一個專門的「介面」類型,用於定義類別必須實現的方法。在 Python 中,我們通常通過抽象類別來模擬介面的功能。抽象類別中的所有方法都是抽象的,子類別必須實現它們。
範例:
1
2
3
4
5
6
7
8
9
10
11
12
13
from abc import ABC, abstractmethod
class Flyable(ABC):
@abstractmethod
def fly(self):
pass
class Bird(Flyable):
def fly(self):
print("Bird is flying.")
bird = Bird()
bird.fly() # 輸出: Bird is flying.
教學重點
- 多型的概念:理解如何通過相同的介面實現不同類別的操作。
- 抽象類別:學會如何使用抽象類別來強制子類別實現特定方法。
abc
模組:學習如何使用abc
模組來定義抽象類別和抽象方法。- 多型與抽象類別的結合:掌握如何通過抽象類別來實現多型,從而設計更靈活的程式架構。
任務
- 創建一個抽象類別
Vehicle
,定義一個抽象方法drive()
,然後創建兩個子類別Car
和Bike
,並實現各自的drive()
方法。 - 創建一個抽象類別
Shape
,定義一個抽象方法perimeter()
,然後創建兩個子類別Square
和Triangle
,並實現計算周長的功能。 - 使用多型創建一個函數
describe_animal(animal)
,接受一個Animal
類別或其子類別的物件,並呼叫speak()
方法來輸出聲音。 - 創建一個抽象類別
Appliance
,並定義抽象方法turn_on()
和turn_off()
,然後創建兩個子類別Fan
和Light
,實現各自的開關功能。