模板方法模式

假如我们有一些对象,各个对象之间有一些相同的行为,也有一些不同的行为,这时,我们就可以用模板方法模式来把相同的部分上移到它们的共同原型中(父类),而将不同的部分留给自己各自重新实现。

模板方法:在这些平行对象的共同原型中定义的一个方法,它封装了子类的算法框架,它作为一个算法的模板,指导子类以何种顺序去执行哪些方法。

模板方法常常被架构师用于搭建项目的框架,架构师定好了框架的骨架,程序员们继承框架的结构后,负责往里面填空。

模板方法模式中,常常用到一个钩子方法:在父类中的容易变化的方法上放置钩子,模板方法依据钩子方法的返回值来决定是否执行容易变化的方法。

模板方法模式是一种基于继承的设计模式,但在JavaScript中也可以通过高阶函数来实现。

基于继承的模板方法模式:

//模板方法模式
//泡茶和冲咖啡,有相似的方法,也有不同的方法
//相似的方法在父类中实现,不同的方法在子类中各自重写
var Beverage = function () {};
Beverage.prototype.boilWater = function () {
console.log('把水煮沸');
};
Beverage.prototype.pourMaterial = function (material) {
console.log('把'+material+'倒进杯子');
};
Beverage.prototype.pourInCup = function () {
console.log('把沸水倒进杯子');
};
Beverage.prototype.addCondiments = function () {
throw new Error('子类必须自行实现该方法');
};
//钩子方法,是否需要加配料
Beverage.prototype.isWantCondiments = function () {
return true; //默认为true,子类自行实现来改变返回值
};
//模板方法,规定了各个方法的执行顺序
Beverage.prototype.init = function (material) {
this.boilWater();
this.pourMaterial(material);
this.pourInCup();
if(this.isWantCondiments()){ //根据钩子方法的返回值决定是否执行
this.addCondiments();
}
};
//====子类
var Coffee = function () {};
Coffee.prototype = new Beverage(coffee);
Coffee.prototype.addCondiments = function () {
console.log('加糖');
};
Coffee.prototype.isWantCondiments = function () {
return window.confirm('请问需要加糖吗?');
};
//调用
var coffee = '咖啡粉';
var coffee1 = new Coffee();
coffee1.init(coffee);

通过高阶函数来实现:

var Beverage1 = function (obj,material) {
var boilWater = function(){
console.log('把水煮沸');
};
var pourMaterial = function(material){
console.log('把'+material+'倒进杯子');
};
var pourInCup = function () {
console.log('把沸水倒进杯子');
};
var addCondiments = obj.addCondiments||function () {
throw new Error('子类必须自行实现该方法');
};
var isWantCondiments = obj.isWantCondiments||function () {
return true; //默认为true,子类自行实现来改变返回值
};
var F = function(){};
F.prototype.init = function(){
boilWater();
pourMaterial(material);
pourInCup();
if(isWantCondiments()){ //根据钩子方法的返回值决定是否执行
addCondiments();
}
};
return F;
};
//定义子类
var Coffee1 = Beverage1({
addCondiments: function(){
console.log('加糖');
},
isWantCondiments: function () {
return window.confirm('请问需要加糖吗?');
}
},'咖啡粉');
var Tea1 = Beverage1({
addCondiments: function(){
console.log('加柠檬');
},
isWantCondiments: function () {
return window.confirm('请问需要加柠檬吗?');
}
},'茶叶');
var aCupOfCoffee = new Coffee1();
aCupOfCoffee.init();
//把水煮沸
//把咖啡粉倒进杯子
//把沸水倒进杯子
//加糖(点确定)
var aCupOfTea = new Tea1();
aCupOfTea.init();
//把水煮沸
//把茶叶倒进杯子
//把沸水倒进杯子
//加柠檬(点确定)

参考文献: 《JavaScript模式》 《JavaScript设计模式与开发实践》

轻松掌握:JavaScript模板方法模式的更多相关文章

  1. javascript模板方法模式

    一:什么是模板方法模式: 模板方法模式由二部分组成,第一部分是抽象父类,第二部分是具体实现的子类,一般的情况下是抽象父类封装了子类的算法框架,包括实现一些公共方法及封装子类中所有方法的执行顺序,子类可 ...

  2. 《JavaScript设计模式与开发实践》读书笔记之模板方法模式

    1. 模板方法模式 1.1 面向对象方式实现模板方法模式 以泡茶和泡咖啡为例,可以整理为下面四步 把水煮沸 用沸水冲泡饮料 把饮料倒进杯子 加调料 首先创建一个抽象父类来表示泡一杯饮料 var Bev ...

  3. 再起航,我的学习笔记之JavaScript设计模式17(模板方法模式)

    模板方法模式 由模板方法模式开始我们正式告别结构型设计模式,开始行为型设计模式的学习分享 行为型设计模式用于不同对象之间职责划分或算法抽象,行为型设计模式不仅仅涉及类和对象,还涉及类或对象之间的交流模 ...

  4. javascript设计模式——模板方法模式

    前面的话 在javascript开发中用到继承的场景其实并不是很多,很多时候喜欢用mix-in的方式给对象扩展属性.但这不代表继承在javascript里没有用武之地,虽然没有真正的类和继承机制,但可 ...

  5. JavaScript设计模式-----模板方法模式

    模板方法模式是一种只需要使用继承就可以实现的非常简单点的模式. 模板方法模式有两部分组成,第一部分是抽象父类,第二部分是具体的实现子类.通常在抽象父类中封装了子类的算法框架,包括实现 一些公共方法以及 ...

  6. [设计模式] javascript 之 模板方法模式

    模板方法模式说明 定义:定义方法操作的骨架,把一些具体实现延伸到子类中去,使用得具体实现不会影响到骨架的行为步骤! 说明:模式方法模式是一个继承跟复用的典型模式,该模式定义了一个抽象类,Abstrac ...

  7. javascript设计模式与开发实践阅读笔记(11)—— 模板方法模式

    模板方法模式: 由两部分结构组成,第一部分是抽象父类,第二部分是具体的实现子类.通常在抽象父类中封装了子类的算法框架,包括实现一些公共方法以及封装子类中所有方法的执行顺序.子类通过继承这个抽象类,也继 ...

  8. javascript设计模式(张容铭)学习笔记 - 照猫画虎-模板方法模式

    模板方法模式(Template Method):父类中定义一组操作算法骨架,而降一些实现步骤延迟到子类中,使得子类可以不改变父类的算法结构的同时可重新定义算法中某些实现步骤. 项目经理体验了各个页面的 ...

  9. PHP设计模式之模板方法模式

    模板方法模式,也是我们经常会在不经意间有会用到的模式之一.这个模式是对继承的最好诠释.当子类中有重复的动作时,将他们提取出来,放在父类中进行统一的处理,这就是模板方法模式的最简单通俗的解释.就像我们平 ...

随机推荐

  1. OpenCascade Chinese Text Rendering

    OpenCascade Chinese Text Rendering eryar@163.com Abstract. OpenCascade uses advanced text rendering ...

  2. java静态代理与动态代理

    原文链接:http://www.orlion.ga/207/ 一.代理模式 代理模式是经常用到的设计模式,代理模式是给指定对象提供代理对象.由代理对象来控制具体对象的引用. 代理模式涉及到的角色: 抽 ...

  3. 浅谈web语义化

    在前端的编程道路上,是否听过html的结构语义化? 是否觉得自己前端嘛,只要做出炫酷的效果,编写出牛逼的JavaScript代码就ok啦.div+css所向无敌,干嘛要用其他标签呢. 是啊,正如上面所 ...

  4. Linux笔记之——Linux关机命令详解(转)

    原文连接:http://www.jb51.net/os/RedHat/1334.html 在linux下一些常用的关机/重启命令有shutdown.halt.reboot.及init,它们都可以达到重 ...

  5. objective-c 语法快速过(6)内存管理原理

    内存管理基本原理(最重要) 移动设备的内存极其有限(iphone 4内存512M),每个app所能占用的内存是有限制的(几十兆而已). 当app所占用的内存较多时,系统会发出内存警告,这时得回收一些不 ...

  6. ajax调用本地wcf中的post和get

    我们可以通过jQuery调用本地或者远程的wcf服务,本文讲解的是对本地wcf服务的post和get调用方式. post和get到底有什么区别呢?此处不作详述. 但是,post对请求的数据格式更为严格 ...

  7. Ajax跨域访问wcf服务中所遇到的问题总结。

    工具说明:vs2012,sql server 2008R2 1.首先,通过vs2012建立一个wcf服务项目,建立好之后.再新开一个vs2012 建立web项目,通过jQuery的ajax方法访问服务 ...

  8. web前端学习随笔

    为什么是随笔 好好算下来,学习web前端已有半个月了,这半个月来主要学习的是HTML和CSS部分,期间有困惑,也有解决困惑时的快感,所以想把这段时间感受到的一些东西记下来,因为内容比较杂,所以干脆叫随 ...

  9. springmvc处理上传图片代码(校验图片尺寸、图片大小)

    package com.maizuo.web.controller; import com.maizuo.domain.Result; import com.maizuo.util.Constants ...

  10. .NET 扩展方法 (一)

    我还记得刚刚学编程的时候,老师经常会提到一句话:注意空指针.所以经常在某些“入口”位置,进行代码校验,空指针的判断就是其中的一项工作. string类型作为常用的数据类型,它在项目中出现的机率极高,所 ...