OOP: Method Resolution Order - Arabic
خاصية الترتيب الوراثي في الـ OOP او المعرف باللغة الانجليزية Method Resolution Order ويختصر لـ MRO.
class A:
def save(self):
print("I'm class A")
class B(A):
pass
class C:
def save(self):
print("I'm class C")
class D(B, C):
pass
الـ Class D بيعمل Multiple inheritance هنتكلم عليها أكثر وسط الكلام.
قولنا قبل كده ان كل حاجة في الـ Python بـ Inherited من الـ Object Class وكده الترتيب الوراثي هنا هيكون D, B, A, C, Object حيث ان:
** D بعد كده من الشمال لليمين B
** B بــ Inherit من A
** فهيكون C والاخير Object
استخدم الـ Attribute التالي عشان تشوف الترتيب بنفسك:
print(D.__mro__)
دلوقتي لو انا عملت Object x من الـ D Class واستدعيت الـ save Method, شوف الكود التالي:
class A:
def save(self):
print("I'm class A")
class B(A):
pass
class C:
def save(self):
print("I'm class C")
class D(B, C):
pass
x = D()
x.save()
, الترتيب الظاهري بيقول انها تستدعى من الـ C لكن الترتيب الوراثي (MRO) يستدعيها من الـ A لانها الاول في الترتيب
دي مشكلة والمشكلة الثانية لما يحصل conflict بــ الـ Inheritance.
هنا هضيف فقط الـ A للـ C
class C(A):
def save(self):
print("I'm class C")
لو عملنا MRO المفروض الترتيب يكون (قراءة من الشمال) D, B, A, C, A, object
لكن لو استخدمت الـ __mro__ هتلاقي الترتيب D, B, C, A, object
الترتيب الأول أسمه Classic MRO وده كان بيستخدم في نسخ Python الـ قبل 2.2 انما الترتيب الحالي اسمه new-style, بيقول .....
ان لو في الـ MRO ظهر نفس الـ Class بيتم حذف كل المكرر عدا الاخير من الترتيب, حيث تم زي ما ظاهر ان لـ A تم حذفه, تقدر تقرا اكتر Method Resolution Order
المطلوب انك متستخدمش الـ Multiple Inheritance لانه Bad Practices الا لو انت عارف بالظبط الـ Output, عموما لغة زي الـ Java مثلآ, مش بتدعم الـ Multiple Inheritance و Framework كبيرة زي الـ Django بتنصح بعدم الاستخدام كذلك.
كذلك هتقابل مصطلح الـ Multilevel Inheritance هو انك تـ Inherit من الـ Derived Class, احنا اتكلمنا عليها قبل كده بس ده مثال للتذكير:
class Base:
pass
class Derived(Base):
pass
class Inherited(Derived):
pass
Consistent MRO Error
قلنا إن الـ Inherit بالـ OOP وبالأخص الـ Python بيبدا من الـ Declared Class لغاية الـ Object, لكن لو الـ Inherit حصل فيه تداخل في بيظهر Error شوف الكود التالي:
class A:
def greeting(self):
print('im the base A')
class B(A):
def greeting(self):
print('im B')
class C(B):
def greeting(self):
print('im C')
class Test(B, C):
pass
بعد كده:
print(Test.__mro__)
هيظهر الرسالة التالية:
TypeError: Cannot create a consistent method resolution order (MRO) for
bases B, C
الـ Error حصل بسبب التالي:
** B نسخة من الـ A
** والـ C نسخة من الـ B
** لما انا عملت (Test(B, C
** طلبت الترتيب (حسب الـ New Style) يكون
** (قراءة من الشمال) Test, C, B, A, object
** يعني تم تجاهل الـ A Base Class
** والـ B Derived Class
يعني الـ Inheritance نفسه غلط, ده بردو من أسباب عدم استخدام الـ Mulieplie Inheritance, اللخبطة.
المقال التالي: Python Super Method
المقال السابق: Inheritance