استبدال المعامل بتوابع صريحة (Replace Parameter with Explicit Methods)

من موسوعة حسوب

المشكلة

ينقسم التابع إلى أجزاء، كل منها يتم تشغيله اعتمادًا على قيمة المعامل.

الحل

استخراج الأجزاء الفردية من التابع إلى توابعها الخاصة واستدعائها بدلًا من استدعاء التابع الأصلي.

مثال

قبل إعادة التصميم

وجود تابع يدعى ()setValue يضبط قيمة الارتفاع والعرض بناءً على تمرير سلسلة نصية صريحة بذلك:

في لغة Java:

void setValue(String name, int value) {
  if (name.equals("height")) {
    height = value;
    return;
  }
  if (name.equals("width")) {
    width = value;
    return;
  }
  Assert.shouldNeverReachHere();
}

في لغة C#‎:

void SetValue(string name, int value) 
{
  if (name.Equals("height")) 
  {
    height = value;
    return;
  }
  if (name.Equals("width")) 
  {
    width = value;
    return;
  }
  Assert.Fail();
}

في لغة PHP:

function setValue($name, $value) {
  if ($name === "height") {
    $this->height = $value;
    return;
  }
  if ($name === "width") {
    $this->width = $value;
    return;
  }
  assert("Should never reach here");
}

في لغة Python:

def output(self, type):
    if name == "banner"
        # Print the banner.
        # ...
    if name == "info"
        # Print the info.
        # ...

بعد إعادة التصميم

استخراج التابع السابق إلى تابعين ()setHeight و ()setWidth يضبط الأول قيمة الارتفاع والثاني قيمة العرض:

في لغة Java:

void setHeight(int arg) {
  height = arg;
}
void setWidth(int arg) {
  width = arg;
}

في لغة C#‎:

void SetHeight(int arg) 
{
  height = arg;
}
void SetWidth(int arg) 
{
  width = arg;
}

في لغة PHP:

function setHeight($arg) {
  $this->height = $arg;
}
function setWidth($arg) {
  $this->width = $arg;
}

في لغة Python:

def outputBanner(self):
    # Print the banner.
    # ...

def outputInfo(self):
    # Print the info.
    # ...

لم إعادة التصميم؟

يعتمد تضخُّم التابع الذي يحتوي على بدائل على المعامل بشكل هائل. تُشغَّل الشيفرة غير التافهة في كل فرع ونادرًا جدًا ما تضاف بدائل جديدة.

فوائد تطبيق الحل

  • تحسين إمكانية قراءة الشيفرة البرمجية. فإنه من الأسهل بكثير فهم الغرض من startEngine()‎ عن setValue("engineEnabled", true)‎.

متى يترك هذا الحل؟

  • لا يُستبدل المعامل بتوابع صريحة إذا كان من النادر تغيير التابع ولا تُضاف بدائل جديدة داخله.

آلية الحل

  1. أنشئ تابعًا منفصلًا لكل بديل لهذا التابع. شغِّل هذه التوابع بناءً على قيمة المعامل في التابع الرئيسي.
  2. ابحث عن كل الأماكن التي يُستدعى فيها التابع الأصلي. ضع في هذه الأماكن استدعاءً لأحد البدائل الجديدة المعتمدة على المعامل.
  3. عندما لا يتبقى أية استدعاءات إلى التابع الأصلي، احذفه.

انظر أيضًا

مصادر