说起设计模式,大家的印象中一定是先想到JAVA中的24种设计模式,其实JavaScript中也有相应的设计模式,今天我们要说的组合模式就是其中的一种。
那么什么是组合模式呢?组合模式你可以理解为一个遥控器。你用到哪个功能就开启哪个功能函数即可。下面我们来看看代码
function Compose(){
this.list = [];
}
首先我们先创建一个构造函数Conpose,然后在里面创建一个list数组,什么?你问我list是干嘛用的,后面你就知道了。之后我们再写出内部函数来
Compose.prototype = {
constructor : Compose,
// 向list之中添加一个功能等待执行;
add : function( cb , options ){
// 把options默认变成对象;
options = options || {};
this.list.push({
cb : cb ,
type : options.type || "default"
});
},
// 直接执行我们需要的功能;
fire : function(){
// 遍历功能列表,实现功能调用;
this.list.forEach( function( item ){
switch (item.type) {
case "default":
item.cb();
break;
case "constructor":
new item.cb();
break;
default:
break;
}
})
}
}
其中,函数add的作用就是将需要添加的功能添加到当前的组合模式中。也就是说我们现在虽然拿到了一个遥控器,但是这是一个空白的遥控器,你得把他的芯片里存的功能内容给放进去,而fire就相当于是遥控器中的按键,用来启动功能用的。下面我们把add函数单独拿出来细讲一下
add : function( cb , options ){
// 把options默认变成对象;
options = options || {};
this.list.push({
cb : cb ,
type : options.type || "default"
});
}
其中,cb就是一个回调函数,用于传入要功能函数,而那个options是给你用于传入其他配置参数,其中,由于options并不是一定要传入的,所以我们要加一句判定options=options||{}
含义就是在options存在时,我们就用options,不存在时置为空。之后我们使用push函数将内容放到list数组中。其中,这里我们为了演示options,所以临时加了一个options.type用于判断类型,当传入一个类型时,就使用传入的类型,当类型不存在时,默认使用default这个值。好的这样我们就把add添加器给写好了,我们将传入的功能成功的放入了list里面存储,但老是存着也不是回事是吧,万一发霉了咋办,所以咱得调用它是吧。所以接下来我们开始使用fire函数,用于调用他们。还是,我们先把fire函数单独拿出来细讲一下
fire : function(){
// 遍历功能列表,实现功能调用;
this.list.forEach( function( item ){
switch (item.type) {
case "default":
item.cb();
break;
case "constructor":
new item.cb();
break;
default:
break;
}
})
}
这里其实也比较简单,我们既然前面已经把功能都放进list里面了,所以既然要调用他的话就要把它遍历一遍是吧,把里面的功能都拿出来。这里我们使用forEach这个API来实行遍历。里面我们传入一个回调函数,我们在里面接收一下item,item的值就是当前list的这个值。之前我们不是提到了说是加入一个type功能来演示一下options的使用嘛,这里我们就可以用到啦。通过switch来判断options.type的值,来调用相应的功能,内容就是如果传入的默认的default的话就直接调用函数即可,如果是构造函数的话我们就需要new一下。
以上我们就成功把这个遥控器给拼装好了。下面我们开始用一下看看好不好使。
function banner(){
console.log("启动banner功能");
}
function table(){
console.log("选项卡");
}
function Menu( a , b){
console.log(this,a,b);
}
function Stairs( a , b){
console.log(this , a , b)
}
这里我们随便写了四个用于测试的函数,以后在实战用使用时,可以放上你自己需要的函数。
然后接下来我们需要把这些函数给放进遥控器里面,当然是使用add函数啦
var com = new Compose();
com.add(banner);
com.add(table);
com.add(Menu.bind(false,"a","b") , { type : "constructor" });
com.add(Stairs , { type : "constructor"});
var com2 = new Compose();
com2.add(banner);
com2.add(Menu.bind(false,"a","b") , { type : "constructor" });
com2.add(Stairs , { type : "constructor"});
setTimeout(function(){
if( Math.random() > 0.5 ){
console.log("VIP用户去广告");
com2.fire();
}else{
console.log("普通用户先看2000s广告");
com.fire();
}
},1000)
这里为了测试,我们new了两个com出来,进行不同的调用,我们让代码跑起来来看看好不好使
OK好使,相应的功能都成功的启动了,是的这就是组合模式了,是不是非常简单呢。设计模式就是为了让我们优雅且高效的实现相应类型的功能,所以我们有的时候需要灵活一下,
使用设计模式来代替老旧的函数。这里我们介绍的组合模式,只是设计模式中的冰山一角。希望可以启发到大家,让各位小伙伴们有所收获呀~