طَبِّقْهاتعلّم المبدأ، وطبّقه بيدكمقرر 111 · أساسيات برمجة الحاسب
الدرس 25 · الوحدة 5: البرمجة الشيئية

الوراثة

نكتب المشترك مرة واحدة في كلاس أب، وترثه الكلاسات الأخرى. ⏱ نحو 20 دقيقة.

PersonStudentTeacher
بعد هذا الدرس ستستطيع أن:
  • تشرح الوراثة بمثال من الحياة.
  • تكتب كلاسًا ابنًا يرث من كلاس أب.
  • تضيف خصائص للابن مع super().__init__.
  • تعيد تعريف دالة الأب في الابن.

١ما الوراثة؟

الطالب والمعلم كلاهما شخص: لكل منهما اسم وعمر، ويستطيع أن يعرّف بنفسه. لكن الطالب له درجة، والمعلم له تخصص. بدل أن نكرر الاسم والعمر في كلاسين، نكتبهما مرة في كلاس أب، ويرثهما الكلاسان الابنان.

main.py
class Person:    def __init__(self, name):        self.name = name     def hello(self):        print("أنا", self.name) class Student(Person):    pass s = Student("ريم")s.hello()
Shell×
>>> %Run main.py
أنا ريم
>>>

class Student(Person) تعني: Student يرث كل ما في Person. لذلك استطاع الكائن s استخدام hello مع أننا لم نكتبها في Student.

٢الابن يضيف ما يخصّه

نضيف للابن دوالًا جديدة لا توجد في الأب:

main.py
class Person:    def __init__(self, name):        self.name = name     def hello(self):        print("أنا", self.name) class Teacher(Person):    def teach(self):        print(self.name, "يشرح الدرس") t = Teacher("أ. ماجد")t.hello()t.teach()
Shell×
>>> %Run main.py
أنا أ. ماجد
أ. ماجد يشرح الدرس
>>>

٣خاصية جديدة مع super

إذا احتاج الابن خاصية جديدة، فإنه يكتب __init__ خاصة به، ويستدعي فيها بناء الأب بـ super().__init__ حتى لا يعيد كتابة ما فيه:

main.py
class Person:    def __init__(self, name):        self.name = name class Student(Person):    def __init__(self, name, mark):        super().__init__(name)        self.mark = mark     def show(self):        print(self.name, "درجته", self.mark) s = Student("خالد", 88)s.show()
Shell×
>>> %Run main.py
خالد درجته 88
>>>

super() تعني «الأب». فالسطر super().__init__(name) يطلب من الأب أن يحفظ الاسم كما يفعل دائمًا.

٤الابن يغيّر سلوك الأب

إذا كتب الابن دالة بالاسم نفسه الموجود في الأب، فإن دالة الابن هي التي تُنفَّذ. هذا اسمه إعادة التعريف:

main.py
class Person:    def __init__(self, name):        self.name = name     def hello(self):        print("أنا", self.name) class Student(Person):    def hello(self):        print("أنا الطالب", self.name) Person("فهد").hello()Student("نورة").hello()
Shell×
>>> %Run main.py
أنا فهد
أنا الطالب نورة
>>>
📎 للاستزادة (اختياري): علاقة «هو نوع من»

استخدم الوراثة إذا صحّ أن تقول: «الطالب نوع من الشخص». أما «السيارة لها محرك» فليست وراثة، بل خاصية داخل الكائن.

توقّع وتحقّق

class Car(Vehicle):. أي الكلاسين هو الأب؟

الأب بين القوسين.

ما فائدة الوراثة؟

نكتب المشترك مرة واحدة.

ماذا تعني super()؟

super تشير إلى الأب.

الأب والابن فيهما دالة hello. أي دالة تُنفَّذ لكائن من الابن؟

دالة الابن تُعيد تعريفها.

الخلاصة

تحدٍّ برمجي: الحيوان والقط

متوسط

اكتب كلاسًا Animal فيه __init__ تحفظ الاسم، ودالة eat تطبع: الاسم ثم «يأكل». ثم كلاسًا Cat يرث من Animal ويضيف دالة meow تطبع «مياو». اصنع قطًّا اسمه «بسبس» واستدعِ eat ثم meow.

المطلوب:
  • class Cat(Animal):
  • دالة eat في الأب فقط.
  • c = Cat("بسبس")

ابدأ من هذا الكود، واضغط ▶ شغّل هنا لتكتب حلّك وتجرّبه مباشرة:

main.py
class Animal:    def __init__(self, name):        self.name = name
المطلوب×
بسبس يأكل
مياو
💡 تلميح 1
print(self.name, "يأكل")
💡 تلميح 2
لا تكتب __init__ في Cat، فهو يرثها.

حاول بنفسك أولًا؛ للمسألة أكثر من حلّ صحيح.

main.py
class Animal:    def __init__(self, name):        self.name = name     def eat(self):        print(self.name, "يأكل") class Cat(Animal):    def meow(self):        print("مياو") c = Cat("بسبس")c.eat()c.meow()
انتقل إلى تقييم الدرساختيار من متعدد، وصح وخطأ، وأكمل الفراغ، وتتبّع الناتج.ابدأ التقييم ←