أهلاً! نواصل استكشاف موضوع الفئات المتداخلة في Java. تحدثنا في التمرين الأخير عن الفئات المتداخلة غير الثابتة، والتي تُعرف أيضًا باسم الفئات الداخلية، واليوم ننتقل إلى مجموعة أخرى من الفئات. سننظر في الفئات المتداخلة الثابتة. كيف تختلف عن الطبقات الأخرى؟ عند الإعلان عن هذا النوع من الفئات، نستخدم الكلمة الأساسية الثابتة التي تعرفها بالفعل:
public class Boeing737 {
private int manufactureYear;
private static int maxPassengersCount = 300;
public Boeing737(int manufactureYear) {
this.manufactureYear = manufactureYear;
}
public int getManufactureYear() {
return manufactureYear;
}
public static class Drawing {
public static int getMaxPassengersCount() {
return maxPassengersCount;
}
}
}
في هذا المثال لدينا Boeing737
الطبقة الخارجية التي تمثل طائرة من هذا النوع. تحتوي على مُنشئ بمعلمة واحدة: سنة الصنع ( int manufactureYear
). يوجد أيضًا متغير ثابت واحد: الحد الأقصى لعدد الركاب ( int maxPassengersCount
). سيكون لها نفس القيمة لجميع المستويات من نفس النموذج، لذلك نحتاج فقط إلى مثيل واحد. بالإضافة إلى ذلك، فهي تحتوي على فئة متداخلة ثابتة: Drawing
(تمثل المخططات الهندسية للطائرة). نحن نستخدم هذه الفئة لتغليف جميع المعلومات الرسمية عن الطائرة. في مثالنا، من أجل التبسيط، قمنا بقصر هذه الفئة على سنة الصنع، ولكنها يمكن أن تحتوي على الكثير من المعلومات الأخرى. كما قلنا في الدرس الأخير، إنشاء مثل هذه الفئة المتداخلة يحسن التغليف ويساهم في تجريد أكثر واقعية. ما الفرق بين الفئات المتداخلة الثابتة وغير الثابتة؟ 1. لا يقوم كائن Drawing
الفئة الثابتة بتخزين مرجع إلى مثيل محدد للفئة الخارجية. تذكر مثال الدراجة من الدرس الأخير:
public class Bicycle {
private String model;
private int maxWeight;
public Bicycle(String model, int maxWeight) {
this.model = model;
this.maxWeight = maxWeight;
}
public void start() {
System.out.println("Let's go!");
}
public class Handlebar {
public void right() {
System.out.println("Steer right!");
}
public void left() {
System.out.println("Steer left!");
}
}
}
تحدثنا في هذا الدرس عن حقيقة أن كل مثيل للطبقة Handlebar
الداخلية، بشكل غير محسوس لنا، يمرر إشارة إلى مثيل الطبقة Bicycle
الخارجية. بدون مثيل للطبقة الخارجية، لا يمكن لكائن الطبقة الداخلية أن يوجد ببساطة. بالنسبة للفئات المتداخلة الثابتة، هذا ليس هو الحال. كائن فئة متداخلة ثابتة قادر تمامًا على الوجود من تلقاء نفسه. في هذا الصدد، تعتبر الفئات الثابتة أكثر "استقلالية" من الفئات غير الثابتة. الشيء الوحيد الذي تحتاج إلى معرفته هو أنه عند إنشاء مثل هذا الكائن، يجب عليك تحديد اسم الفئة الخارجية:
public class Main {
public static void main(String[] args) {
Boeing737.Drawing drawing1 = new Boeing737.Drawing();
Boeing737.Drawing drawing2 = new Boeing737.Drawing();
}
}
لماذا جعلنا الفصل ثابتًا عندما جعلنا الفصل (الذي يمثل مقعد الدراجة) غير ثابت Drawing
في الدرس الأخير ؟ Seat
مثل المرة السابقة، دعونا نضيف القليل من "الفلسفة" لفهم المثال :) على عكس مقعد الدراجة، فإن مفهوم الرسم الهندسي ليس مرتبطًا بشكل صارم بمفهوم الطائرة. بدون دراجة، غالبًا ما يكون مقعد الدراجة المنفصل بلا معنى (على الرغم من أنه ليس دائمًا، تحدثنا عن هذا في الدرس الأخير). مفهوم الرسم الهندسي منطقي في حد ذاته. على سبيل المثال، قد يكون مفيدًا للمهندسين الذين يخططون لصيانة الطائرات. ليست هناك حاجة للطائرة لوضع الخطة ويمكن أن تكون موجودة في أي مكان. مطلوب الرسم الهندسي فقط . بالإضافة إلى ذلك، فإن جميع الطائرات من نفس الطراز سيكون لها نفس الرسم الهندسي، لذلك لا توجد علاقة وثيقة مثل تلك الموجودة مع مقعد الدراجة. لذلك، Drawing
لا يحتاج الكائن إلى مرجع إلى كائن طائرة محدد. 2. الوصول إلى متغيرات وأساليب الطبقة الخارجية المختلفة. يمكن للفئة المتداخلة الثابتة الوصول فقط إلى الحقول الثابتة للفئة الخارجية. في مثالنا، Drawing
لدى الفئة getMaxPassengersCount()
طريقة تُرجع قيمة maxPassengersCount
المتغير الثابت للفئة الخارجية. ومع ذلك، لا يمكننا إنشاء getManufactureYear()
طريقة في Drawing
الفصل لإرجاع قيمة manufactureYear
. بعد كل شيء، manufactureYear
المتغير غير ثابت، مما يعني أنه يجب أن ينتمي إلى نسخة محددة من Boeing737
. وكما اكتشفنا بالفعل، في حالة الفئات المتداخلة الثابتة، قد يكون كائن الطبقة الخارجية غائبًا بسهولة. ومن ثم، فإن القيد :) لا يهم معدل الوصول الذي يحتوي عليه المتغير الثابت في الفئة الخارجية. حتى لو كان الأمر كذلك private
، فسيظل بإمكان الفئة المتداخلة الثابتة الوصول. كل ما سبق لا ينطبق فقط على الوصول إلى المتغيرات الثابتة، ولكن أيضًا على الأساليب الثابتة. مهم! في الإعلان عن فئة داخلية، static
لا تعني الكلمة الأساسية أنه يمكنك إنشاء كائن واحد فقط. لا تخلط بين الكائنات والمتغيرات. إذا كنا نتحدث عن المتغيرات الثابتة، فنعم، يوجد مثيل واحد لمتغير فئة ثابتة، على سبيل المثال، maxPassangersCount
. ولكن عند static
تطبيقه على فئة متداخلة، فهذا يعني فقط أن كائناتها لا تحتوي على مراجع لكائنات الفئة الخارجية. ويمكننا إنشاء العديد من الكائنات بنفسها كما نريد:
public class Boeing737 {
private int manufactureYear;
private static int maxPassengersCount = 300;
public Boeing737(int manufactureYear) {
this.manufactureYear = manufactureYear;
}
public int getManufactureYear() {
return manufactureYear;
}
public static class Drawing {
private int id;
public Drawing(int id) {
this.id = id;
}
public static int getPassengersCount() {
return maxPassengersCount;
}
@Override
public String toString() {
return "Drawing{" +
"id=" + id +
'}';
}
public static void main(String[] args) {
for (int i = 1; i < 6; i++) {
Boeing737.Drawing drawing = new Boeing737.Drawing(i);
System.out.println(drawing);
}
}
}
}
لقد أعلنا عن main()
الطريقة مباشرة في الفئة المتداخلة (لا يوجد سبب خاص لذلك - فقط لإعلامك بأن هذا ممكن)، وقمنا بإنشاء 5 Drawing
كائنات. على الرغم من أنه ليس لدينا كائن واحد من الطبقة الخارجية. كما ترون، هذا لم يخلق أي مشاكل :) إخراج وحدة التحكم:
Drawing{id=1}
Drawing{id=2}
Drawing{id=3}
Drawing{id=4}
Drawing{id=5}
وبهذا اختتم درسنا! تحسبًا لذلك، سأترك لك رابطًا للقسم المتعلق بها في وثائق Oracle
. إذا كان هناك شيء لا يزال غير واضح، فاقرأه. الآن حان الوقت بالنسبة لي لحل بعض المهام! :)
GO TO FULL VERSION