Javascript:配置模式

Javascript: Configuration Pattern

本文关键字:模式 配置 Javascript      更新时间:2023-09-26

问题:Javascript函数只需要几个参数即可使用:

function kick(person, reason, amount) {
    // kick the *person* with the *amount*, based on the *reason*
}

由于没有办法像在Java中那样在JS中进行函数重载,如果它需要设计为便于将来改进(添加参数(,它可以写成:

/* Function Parameters pattern */
function kick() {
    // kick the person as in *arguments[0]*, with the amount as in *arguments[1]*,
    // based on the reason as in *arguments[2]*, with the strength as in *arguments[3]*
}

/* Object Configuration Pattern */
function kick(config) {
    // kick the person as in *config.person*, with the amount as in *config.amount*,
    // based on the reason as in *config.reason*, with the strength as in *config.strength*
}

我知道对象配置模式允许对任何默认属性进行扩充。

因此,问题是:如果I不需要用参数来增强任何属性,那么使用所提出的解决方案中的任何一个而不是另一个是否有任何重要的原因?

使用对象有几个优点:

1.代码可读性更强

考虑以下两个调用:

kick({user: u,
      reason: "flood",
      log: true,
      rejoin: false,
      timeout: 60000,
      privmessage: true});
kick(u, "flood", true, false, 60000, true);

想象一下其他人在读电话。什么是第一个true?还要注意,几个月后你自己也会处于同样的确切位置(不记住kick的第四个参数是什么与不知道它非常相似(。

2.您可以通过隧道参数

使用对象方法,您可以向函数传递一组参数,该函数必须使用这些参数来调用另一个函数

function kickgroup(users, parms) {
    for (var i=0; i<users.lenght; i++) {
        var uparms = Object.create(parms);
        uparms.user = users[i];
        kick(uparms);
    }
}

还要注意,在arguments的情况下,您不需要使用arguments[x]语法来惩罚自己。您只需声明参数并随着函数的发展添加它们:任何尚未传递的参数都将被设置为undefined(如果需要,您仍然可以访问arguments.length来区分调用方是否明确传递了您的函数undefined(。

您不必严格遵守这三者中的任何一个。如果您看看jQuery是如何做到这一点的,它会检查参数的类型、数量和位置,以确定使用了函数的哪种重载风格。

假设你有三种风格的kick(),一种是接受person、reason和amount,另一种是只接受带有reason和amount的person获取默认值,另一个是接受至少有一个人的配置对象

function kick(person, reason, amount) {
    if (person.person) {
       // must be an object as the first parameter
       // extract the function parameters from that object
       amount = person.amount;
       reason = person.reason;
    }
    amount = amount || 5;           // apply default value if parameter wasn't passed
    reason = reason || "dislike";   // apply default value if parameter wasn't passed
    // now you have person, reason and amount and can do normal processing
    // you could have other parameters too
    // you just have to be to tell which parameter is which by type and position
    // process the kick here using person, reason and amount
}

JavaScript函数仅通过其名称进行签名。

因此你可以做:

  function kick(x, reason, amount) {
      if(reason && amount) {
          // do stuff with x as person, reason and amount
      }
      else if(x) {
          // do stuff with x as config
      }
      else {
         // do stuff with no parameters
      }
    }

另一种解决方案是使用arguments变量,它是一个数组,包含传递给javascript 中函数的所有参数

   function kick() {
            alert(arguments.length);
   }