التعريف: يجب أن يعرف كائن واحد أقل عن الكائنات الأخرى
المفهوم الأساسي لقانون ديميتري هو الفصل بين الطبقات والاقتران الضعيف. فقط بعد الاقتران الضعيف يمكن تحسين قابلية الاستخدام في الطبقات.
يشبه الاستعارة الأكثر حيوية: يجب ألا يتصل السجناء في السجن بأشخاص في الخارج ، بالطبع قد يكون هناك أقارب زيارة. السجن هنا هو الفصل ، والسجناء في الداخل هم المعلومات الموجودة داخل الفصل ، ويعادل حراس السجون في السجن إنفاذ قانون ديميت.
يدعي قانون ديميت:
(1) من حيث قسم الطبقة ، يجب إنشاء فئات ذات اقتران ضعيف ؛
(2) في تصميم هيكل الفصل ، يجب على كل فصل تقليل حقوق الوصول للأعضاء ؛
(3) في تصميم الفصل ، إن أمكن ، يجب تصميم فئة كفئة لم تتغير ؛
(4) من حيث الإشارات إلى فئات أخرى ، يجب تقليل مراجع كائن إلى كائنات أخرى ؛
(5) حاول تقليل حقوق الوصول إلى الفصل ؛
(6) استخدام وظيفة التسلسل بحذر ؛
(7) لا تعرض أعضاء الفصل ، ولكن توفير الملحق المقابل (الخصائص).
لإعطاء مثال: هناك شركة جماعية ، والوحدات الفرعية لها فروع وإدارات مباشرة. الآن مطلوب طباعة معرفات الموظف لجميع الوحدات التابعة. دعونا أولاً نلقي نظرة على التصميم الذي ينتهك قاعدة Dimit.
// رئيس موظف فئة المكتب الرئيسي {معرف السلسلة الخاصة ؛ public void setId (string id) {this.id = id ؛ } السلسلة العامة getId () {return id ؛ }} // فرع الموظف الفئة الفرعية {معرف السلسلة الخاصة ؛ public void setId (string id) {this.id = id ؛ } السلسلة العامة getId () {return id ؛ }} class subCompanyManager {list public <subemployee> getAllemplyee () {list <SubeMployee> list = new ArrayList <subeMployee> () ؛ لـ (int i = 0 ؛ i <100 ؛ i ++) {subemployee emp = new subemployee () ؛ // تعيين معرف للموظفين الفرعي بالترتيب Emp.SetId ("الفرع"+i) ؛ list.add (EMP) ؛ } قائمة الإرجاع ؛ }} classeManager {list public list <evelope> getAlleMployee () {list <evelope> list = new ArrayList <evelope> () ؛ لـ (int i = 0 ؛ i <30 ؛ i ++) {experiese emp = new efferene () ؛ // تعيين معرف لموظفي المكتب الرئيسي بالترتيب Emp.SetId ("Head Company"+I) ؛ list.add (EMP) ؛ } قائمة الإرجاع ؛ } public void printallemplyee (subCompanyManager sub) {list <subeMployee> list1 = sub.getAllEmployee () ؛ لـ (subployee e: list1) {system.out.println (e.getId ()) ؛ } قائمة <evelope> list2 = this.getAllEmployee () ؛ لـ (الموظف e: list2) {system.out.println (e.getId ()) ؛ }}} client client {public static void main (string [] args) {companyManager e = new CompanyManager () ؛ E.PrintAllemployee (SubCompanyManager () جديد) ؛ }} المشكلة الرئيسية لهذا التصميم هي الآن في شركة CompanyManager. وفقًا لقانون ديميت ، يحدث التواصل مع الأصدقاء المباشر فقط ، ولفس الموظف الفرعي ليس صديقًا مباشرًا لفئة CompanyManager (الاقتران الذي يظهر كمتغيرات محلية لا ينتمي إلى أصدقاء مباشرين). من الناحية المنطقية ، يجب أن يقترن المكتب الرئيسي فقط بفرعه وليس له صلة بموظفي الفرع. من الواضح أن هذا التصميم يضيف اقتران غير ضروري. وفقًا لقانون ديميت ، يجب تجنب اقتران علاقة الأصدقاء غير المباشرة في الفصل. الرمز المعدل كما يلي:
class subcompanymanager {public list <subemployee> getAlleMployee () {list <subemployee> list = new ArrayList <SubEmployee> () ؛ لـ (int i = 0 ؛ i <100 ؛ i ++) {subemployee emp = new subemployee () ؛ // تعيين معرف للموظفين الفرعي بالترتيب Emp.SetId ("الفرع"+i) ؛ list.add (EMP) ؛ } قائمة الإرجاع ؛ } public void printeMployee () {list <SubeMployee> list = this.getAllEmployee () ؛ لـ (subployee e: list) {system.out.println (e.getId ()) ؛ }}} ClasseManager {قائمة عامة <evelope> getAllEmployee () {list <evelope> list = new ArrayList <evelope> () ؛ لـ (int i = 0 ؛ i <30 ؛ i ++) {experiese emp = new efferene () ؛ // تعيين معرف لموظفي المكتب الرئيسي بالترتيب Emp.SetId ("Head Company"+I) ؛ list.add (EMP) ؛ } قائمة الإرجاع ؛ } public void printallemplyee (subCompanyManager sub) {sub.printemplyee () ؛ قائمة <evelope> list2 = this.getAllEmployee () ؛ لـ (الموظف e: list2) {system.out.println (e.getId ()) ؛ }}} بعد التعديل ، تمت إضافة طريقة طباعة معرف الموظفين إلى الفرع ، ودعا المكتب الرئيسي مباشرة للطباعة ، وبالتالي تجنب الاقتران مع موظفي الفرع.
القصد الأصلي لقانون dimitter هو تقليل الاقتران بين الطبقات. نظرًا لأن كل فصل يقلل من التبعيات غير الضرورية ، فمن الممكن بالفعل تقليل علاقات الاقتران. لكن كل شيء له معاييره الخاصة. على الرغم من أنه يمكن أن يتجنب التواصل مع الأنواع غير المباشرة ، من أجل التواصل ، ستتصل حتماً بالفرع من خلال "وسيط". على سبيل المثال ، في هذه الحالة ، يتصل المكتب الرئيسي بموظفي الفرع من خلال الفرع باعتباره "الوسيط". سيؤدي الاستخدام المفرط لمبدأ DIMIT إلى عدد كبير من فئات الوسائط والنقل ، مما يؤدي إلى تعقيد أكبر للنظام. لذلك ، عند تبني قانون ديميتر ، يجب أن نزن المقايضات مرارًا وتكرارًا ، مما لا يضمن بنية واضحة فحسب ، بل يتطلب أيضًا تماسكًا عالًا وارتفاع اقتران.