多重継承の演習
Python では、クラスが複数の親クラスから継承することを許可されています。これは**多重継承(multiple inheritance)**と呼ばれます。これは異なるソースからの機能を組み合わせる強力なツールになり得ますが、特に同じ名前のメソッドがある場合に Python がどの親のメソッドを使用するかを決定する方法において、複雑さも生じさせます。
この検索順序は**メソッド解決順序(Method Resolution Order, MRO)**と呼ばれます。Python は、一貫性があり予測可能な MRO を決定するために、C3 線形化(C3 linearization)と呼ばれるアルゴリズムを使用します。
新しい例でこれを探求しましょう。ファイルエクスプローラーから multiple_inheritance.py ファイルを開き、以下のコードを追加してください。
## File: multiple_inheritance.py
class ParentA:
def speak(self):
print("Speaking from ParentA")
def common_method(self):
print("ParentA's common method")
class ParentB:
def speak(self):
print("Speaking from ParentB")
def common_method(self):
print("ParentB's common method")
## Child は A の後に B を継承します
class Child_AB(ParentA, ParentB):
pass
## Child は B の後に A を継承します
class Child_BA(ParentB, ParentA):
def common_method(self):
print("Child_BA's own common method")
if __name__ == "__main__":
child1 = Child_AB()
child2 = Child_BA()
print("--- Investigating Child_AB (ParentA, ParentB) ---")
child1.speak()
child1.common_method()
## .mro() メソッドはメソッド解決順序を示します
print("MRO for Child_AB:", [c.__name__ for c in Child_AB.mro()])
print("\n--- Investigating Child_BA (ParentB, ParentA) ---")
child2.speak()
child2.common_method()
print("MRO for Child_BA:", [c.__name__ for c in Child_BA.mro()])
ファイルを保存します。ここで、Child_AB は ParentA の後に ParentB を継承します。Child_BA は逆順に継承します。メソッドが呼び出されると、Python は MRO によって指定された順序でそれを検索します。
ターミナルからスクリプトを実行します。
python multiple_inheritance.py
以下の出力が表示されます。
--- Investigating Child_AB (ParentA, ParentB) ---
Speaking from ParentA
ParentA's common method
MRO for Child_AB: ['Child_AB', 'ParentA', 'ParentB', 'object']
--- Investigating Child_BA (ParentB, ParentA) ---
Speaking from ParentB
Child_BA's own common method
MRO for Child_BA: ['Child_BA', 'ParentB', 'ParentA', 'object']
出力から、以下のことが観察できます。
child1.speak() は Child_AB の MRO で ParentA が最初に来るため、ParentA のメソッドを呼び出します。
child2.speak() は Child_BA の MRO で ParentB が最初に来るため、ParentB のメソッドを呼び出します。
child2.common_method() は、Python が親クラスをチェックする前に Child_BA で直接定義されているバージョンを見つけるため、それを呼び出します。
多重継承のシナリオで動作を予測するためには、MRO を理解することが極めて重要です。