设计模式-模板方法模式

模板方法模式定义

模板方法模式由两部分组成,第一部分是抽象父类,第二部分是具体实现的子类。通常在抽象父类中封装了子类的算法框架,包括实现一些公共方法以及封装子类中所有方法的执行顺序。子类通过继承这个抽象类,也继承了整个算法结构,并且可以选择重写父类的方法。
总的来说,模板方法模式就是将多个模型抽象化归一,从中抽象提取出来一个最基础的模板,这个模板可以作为实体对象也可以作为抽象对象,然后其他模块只需要继承这个模板方法,也可以拓展某些方法。

好莱坞原则

好莱坞原则是指底层组件将自己挂钩到高层组件中,由高层组件决定什么时候、以何种方式去使用这些底层组件。模板方法模式就是好莱坞原则的一个经典使用场景,当我们用模板方法模式编写一个程序时,就意味着子类放弃了对自己的控制权,而改为父类通知子类,哪些方法应该在什么时候被调用。作为子类,只提供一些设计上的细节。
除此之外,好莱坞原则还常常应用于 发布-订阅模式回调函数

模板方法模式实例

弹出框

弹出框的种类有很多种,基础的提示框,带有标题的提示框,取消按钮提示框等等,在这些弹出框中,基础的提示框就是我们要提取出来的基类,因为其他提示框都是在这个提示框的基础上增加一些功能,比如标题组件,取消按钮等。

//基类
var Dialog = function(data) {
    this.content = data && data.content?data.content:"提示内容";
    //提示面板
    this.pannel = document.createElement("div");
    //提示内容组件
    this.contentNode = document.createElement("p");
    this.contentNode.innerHTML = this.content;
    //确定按钮
    this.confirmBtn = document.createElement("span");
    this.confirmBtn.className = "confirm-btn";
    this.confirmBtn.innerHTML = data && data.confirm?data.confirm:"确定";
    //关闭按钮
    this.closeBtn = document.createElement("b");
    this.closeBtn.className = "close-btn";

    //确认回调
    this.success = data.success || function(){};
    //关闭回调
    this.fail = data.fail || function(){};
    
}

Dialog.prototype = {
    init:function() {
        this.pannel.appendChild(this.contentNode);
        this.pannel.appendChild(this.confirmBtn);
        this.pannel.appendChild(this.closeBtn);
        document.body.appendChild(this.pannel);
        //绑定事件
        this.bindEvent();
    }
    bindEvent:function() {
        var _self = this;
        this.closeBtn.onclick = function(){
            _self.fail();
            _self.hide();
        }
    },
    hide:function() {
        this.pannel.style.display = "none";
    },
    show:function() {
        this.pannel.style.display = "block";
    }
}

然后可以根据需要拓展其他类型的弹出框,例如带有标题的提示框

var TitleDialog = function(data) {
    Dialog.call(this,data);
    this.title = data && data.title?data.title:"标题";
    this.titleNode = document.createElement("h3");
    this.titleNode.innerHTML = this.title;
    this.titleNode.className = "title";
}
//继承提示框方法
TitleDialog.prototype = new Dialog;
//重写 init方法拓展标题组件
TitleDialog.prototype.init = function() {
    this.pannel.insertBefore(this.titleNode,this.pannel.firstChild);
    Dialog.prototype.init.call(this);
}

TitleDialog作为Dialog的继承类,也可以作为其他提示框的模板类,例如如果想创建带有标题且带有取消按钮的提示框就可以继承TitleDialog,然后在构造函数中创建一个取消按钮,在原型方法的实例化方法init中加入取消按钮,以及对绑定事件bindEvent方法进行拓展即可。

var CancleBtn = function(data) {
    TitleDialog.call(this,data);
    this.cancle = data && data.cancle?data.cancle:"取消";
    this.cancleNode = document.createElement('span');
    this.cancleNode.innerHTML = this.cancle;
    this.cancleNode.className = "cancle";
}
CancleBtn.prototype = new TitleDialog();
CancleBtn.prototype.init = function() {
    TitleDialog.prototype.init.call(this);
    this.pannel.appendChild(this.cancleNode);
}
CancleBtn.prototype.bindEvent = function() {
    var _self = this;
    TitleDialog.prototype.bindEvent.call(this);
    this.cancleNode.onclick = function() {
        _self.fail();
        _self.hide();
    }
}

使用方式如下:

new CancleBtn({
    title:"标题内容",
    content:"文本",
    cancle:"取消",
    success:function(){//成功回调},
    fail:function(){//取消或关闭回调}
}).init();

小结

模板方法模式的核心在于方法的重用,它将核心方法封装在基类中,让子类继承基类的方法,实现基类方法共享。这种设计模式基类封装的方法通常是不变的算法或者具有稳定的调用方式,约束了子类的行为。当然,子类继承的方法是可以通过对方法重写进行拓展的,但为了让基类对子类有更稳健的约束力,我们要把握好这种拓展。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值