الدرس 23: تعدد الأشكال 2: فهم التحويل
عند استخدام المراجع متعددة الأشكال، تقيد Java الوصول فقط إلى الدوال المعرفة في نوع المرجع (فئة الأب). للوصول إلى الدوال الخاصة بالكائن الابن الفعلي، يجب علينا استخدام التحويل (casting).
1. التحويل للأعلى (Upcasting - ضمني)
تعيين كائن من فئة فرعية إلى متغير مرجعي من فئة الأب يسمى التحويل للأعلى. هذا آمن وتلقائي لأن الفئة الفرعية مضمونة لامتلاك جميع أعضاء فئة الأب.
java class Manager extends Employee { /* ... */ }
Employee emp = new Manager(); // يحدث Upcasting ضمنياً
2. التحويل للأسفل (Downcasting - صريح)
تعيين مرجع فئة الأب إلى متغير مرجعي من فئة فرعية يتطلب تحويلاً صريحاً. هذا يحتمل أن يكون غير آمن، لأنك قد تحاول تحويل كائن أب عام إلى نوع ابن معين ليس منه.
java Employee emp2 = new Manager();
// Downcasting: نخبر المترجم صراحة أننا نعرف أنه Manager. Manager mgr = (Manager) emp2; // الآن يمكن لـ 'mgr' الوصول إلى دوال Manager الخاصة
// مثال تحذيري: Employee emp3 = new Employee(); // Manager badMgr = (Manager) emp3; // خطأ في وقت التشغيل! ClassCastException
3. التحقق من نوع الكائن (instanceof)
قبل التحويل للأسفل، يجب عليك دائماً التحقق من نوع الكائن الفعلي باستخدام المعامل instanceof لمنع حدوث ClassCastException.
java Vehicle v = new Truck();
if (v instanceof Truck) { System.out.println("The object is a Truck, safe to downcast."); Truck t = (Truck) v; t.loadCargo(); // الوصول لدالة خاصة بـ Truck } else { System.out.println("The object is not a Truck."); }
ملاحظة حول Java الحديثة (JDK 16+): قدمت Java مطابقة الأنماط لـ instanceof ، مما يبسط خطوة التحويل:
java if (v instanceof Truck t) { // يتم تحويل 't' تلقائياً إذا كان الشرط صحيحاً t.loadCargo(); }