سؤال

فرضية

أعتقد أن هناك طريقة لتعريف تقنيات التصميم الشيئية "الجيدة" و"السيئة" بشكل موضوعي، وأنه يمكننا كمجتمع تحديد ما هي هذه التقنيات.هذا تمرين أكاديمي.إذا تم القيام بذلك بجدية وتصميم، أعتقد أنه يمكن أن يكون ذا فائدة كبيرة للمجتمع ككل.سيستفيد المجتمع من وجود مكان يمكننا جميعًا الإشارة إليه لنقول، "هذه التقنية جيدة أو سيئة ويجب علينا أو لا نستخدمها ما لم تكن هناك ظروف خاصة."

يخطط

في هذا الجهد، يجب أن نركز على المبادئ الموجهة للكائنات (على عكس اللغات الوظيفية أو القائمة على المجموعة أو أي نوع آخر من اللغات).

لا أخطط لقبول إجابة واحدة، وبدلاً من ذلك أود أن تساهم الإجابات في المجموعة النهائية أو أن تكون مناقشة عقلانية للقضايا.

أدرك أن هذا قد يكون مثيرًا للجدل، لكنني أعتقد أنه يمكننا تسوية شيء ما.هناك استثناءات لمعظم القواعد وأعتقد أن هذا هو المكان الذي سيقع فيه الخلاف.ويتعين علينا أن نصدر تصريحات ثم نسجل الاستثناءات والاعتراضات ذات الصلة من جانب المنشقين.

أساس

أود أن أحاول تعريف "الجيد" و"السيئ":

  • "جيد" - ستعمل هذه التقنية في المرة الأولى وستكون حلاً دائمًا.سيكون من السهل تغييره لاحقًا وسيدفع استثمار الوقت في تنفيذه بسرعة.ويمكن تطبيقه باستمرار ويمكن لمبرمجي الصيانة التعرف عليه بسهولة في المستقبل.بشكل عام، فإنه يساهم في الأداء الجيد ويقلل تكلفة الصيانة طوال عمر المنتج.

  • "سيئ" - قد تنجح هذه التقنية على المدى القصير، ولكنها سرعان ما تصبح عائقًا.من الصعب التغيير على الفور أو يصبح أكثر صعوبة بمرور الوقت.قد يكون الاستثمار الأولي صغيرًا أو كبيرًا، ولكنه سرعان ما يصبح تكلفة متزايدة، وفي النهاية يصبح تكلفة غارقة ويجب إزالته أو العمل عليه باستمرار.يتم تطبيقه بشكل ذاتي وغير متسق وقد يكون مفاجئًا أو لا يمكن لمبرمجي الصيانة التعرف عليه بسهولة في المستقبل.بشكل عام، فإنه يساهم في التكلفة المتزايدة النهائية لصيانة و/أو تشغيل المنتج ويمنع أو يمنع إجراء تغييرات على المنتج.ومن خلال تثبيط التغيير أو منعه، فإنه لا يصبح مجرد تكلفة مباشرة، بل إنه تكلفة فرصة بديلة ومسؤولية كبيرة.

بداية

كمثال على الشكل الذي أعتقد أن المساهمة الجيدة ستبدو عليه، أود أن أقترح مبدأ "جيد":

فصل المخاوف

[وصف قصير]

مثال

[الكود أو أي نوع آخر من الأمثلة]

الأهداف

[شرح المشاكل التي يمنعها هذا المبدأ]

القابلية للتطبيق

[لماذا وأين ومتى أستخدم هذا المبدأ؟]

الاستثناءات

[متى لا أستخدم هذا المبدأ، أو أين قد يكون ضارًا بالفعل؟]

اعتراضات

[لاحظ أي آراء أو اعتراضات مخالفة من المجتمع هنا]

هل كانت مفيدة؟

المحلول

فصل المخاوف

تفضل التجميع على الميراث بأسلوب Mixin

بينما يمكن الحصول على الوظائف عن طريق الوراثة من فئة المرافق، في كثير من الحالات يمكن الحصول عليها جميعًا باستخدام عضو في الفئة المذكورة.

مثال (Boost.Noncopyable):

Boost.Noncopyable هي فئة C++ تفتقر إلى مُنشئ النسخ أو عامل المهمة.يمكن استخدامه كفئة أساسية لمنع نسخ الفئة الفرعية أو تعيينها (هذا هو السلوك الشائع).ويمكن استخدامه أيضًا كعضو مباشر

تحويل هذا:

class Foo : private boost::noncopyable { ... };

الى هذا:

class Foo {
    ...
private:
    boost::noncopyable noncopyable_;
};

مثال (كائن قابل للقفل):

قدمت جافا synchronized الكلمة الأساسية كمصطلح للسماح باستخدام أي كائن بطريقة آمنة.يمكن عكس ذلك في لغات أخرى لتوفير كائنات المزامنة للكائنات العشوائية.ومن الأمثلة الشائعة هياكل البيانات:

class ThreadsafeVector<T> : public Vector<T>, public Mutex { ... };

وبدلا من ذلك، يمكن تجميع الفئتين معا.

struct ThreadsafeVector<T> {
    Vector<T> vector;
    Mutex mutex;
}

الأهداف

كثيرا ما يتم إساءة استخدام الميراث كآلية لإعادة استخدام التعليمات البرمجية.إذا تم استخدام الوراثة لأي شيء إلى جانب العلاقة Is-A، فسيتم تقليل وضوح التعليمات البرمجية بشكل عام.

مع السلاسل الأعمق، تزيد فئات mixin الأساسية بشكل كبير من احتمالية حدوث سيناريو "Diamond of Death"، حيث ينتهي الأمر بالفئة الفرعية إلى وراثة نسخ متعددة من فئة mixin.

القابلية للتطبيق

أي لغة تدعم الوراثة المتعددة.

الاستثناءات

أي حالة توفر فيها فئة mixin أو تتطلب زيادة التحميل على الأعضاء.في هذه الحالة، يشير الميراث عادةً إلى وجود علاقة "يتم تنفيذه ضمن شروط"، ولن يكون التجميع كافيًا.

اعتراضات

قد تؤدي نتيجة هذا التحول إلى أعضاء عامين (على سبيل المثال. MyThreadSafeDataStructure قد يكون في متناول الجمهور Mutex كمكون).

نصائح أخرى

هناك بعض المبادئ المفهومة جيدًا والتي قد تشكل نقطة انطلاق جيدة:

من الجيد أيضًا دراسة أنماط التصميم الحالية للعثور على المبادئ التي تقف وراءها، وأهمها (بشكل عام) تفضيل التركيب على الميراث.

أعتقد أن الإجابة المختصرة هي أن تصميمات OO "الجيدة" تكون قوية في ظل التغيير، مع أقل قدر من كسر التعليمات البرمجية لأي تغيير في المتطلبات.إذا نظرت إلى جميع القواعد المعتادة، فستجدها جميعًا تتجه إلى نفس النتيجة.

تكمن الصعوبة في أنه لا يمكنك تقييم "جودة" التصميم بدون سياق؛أعتقد أنها نظرية مفادها أنه بالنسبة لأي نمطية، يوجد تغيير في المتطلبات من شأنه أن يزيد من الكسر، مما يتسبب في لمس كل فئة في كل طريقة.

إذا كنت تريد أن تكون صارمًا بشأن هذا الأمر، فيمكنك تطوير مجموعة من "حالات التغيير" وترتيبها بترتيب الاحتمالية، بحيث يمكنك تقليل الكسر لأعلى التغييرات الاحتمالية.

ومع ذلك، في معظم الحالات، يساعد الحدس المتطور كثيرًا:تميل الأشياء الخاصة بالجهاز أو النظام الأساسي إلى التغيير، وتميل قواعد العمل وإجراءات العمل إلى التغيير، في حين أن تطبيقات الحساب، على سبيل المثال، نادرًا ما تتغير.(ليس كما قد تتخيل، أبدًا.خذ بعين الاعتبار، على سبيل المثال، نظام أعمال قد يكون أو لا يكون قادرًا على الاستفادة من حسابات BCD المدعومة بالمنصة.)

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top