最近在学习JavaScript设计模式,学习过之后感觉很有收获,现把自己的学习内容总结如下:

模式:是一种可服用的解决方案,可用于解决软件设计中遇到的常见问题。
设计模式:有三大好处,模式是已经验证的解决方案;模式很容易被复用;模式富有表达力。

本篇主要介绍8种设计模式,其余模式将在后续博文中继续介绍。

一、Constructor(构造器)模式

Constructor是一种在内存已分配给对象的情况下,用于初始化新建对象的特殊方法

1、给对象赋键值的方法

(1)“点”语法

newObject.someKey = "Hello Vicky"; 

(2)中括号法

newObject[someKey] = "Hello Vicky";

(3)Object.defineProperty

Object.defineProperty(newObject,"someKey",{value     : "Hello Vicky",writable  : true,enumerable: true
})

(4)Object.defineProperties

Object.defineProperties(newObject,{"someKey":{value     : "Hello Vicky",writable  : true,enumerable: true},"anotherKey":{ //···}
})

2、基本Construtor

在构造器内,this关键字引用新创建的对象

//Constuctor模式很简单,只举个简单的小例子
function Car (model,name) {this.model = model;this.name  = name;this.toString = function () {return this.model + "is named" + this.name;};
}var car = new Car("car","BMW");
console.log(car.toString());//car is named BMW.

上述代码的缺点在于所有实例共享toString()方法,可以用原型来改写一下,就变成了 构造函数-原型组合。可参考之前博文,不再赘述。

二-1、Module(模块)模式

模块是任何强大的应用程序架构中不可或缺的一部分,它通常能够帮助我们清晰的分离和组织项目中的代码单元。

1、JavaScript中用于实现模块的方法

(1)对象字面量

(2)Module模式

(3)AMD模块

(4)CommonJS模块

(5)ECMAScript Harmony模块

2、Module模式

Module模式在某种程度上可以说是基于对象字面量的,该模式返回一个对象,很类似于一个立即调用的函数表达式

Module模式:用于进一步模拟类的概念,通过这种方式,能够使一个单独的对象拥有共有/私有方法和变量,从而屏蔽来自全局作用域的特殊部分。
Module模式使用闭包封装“私有”状态和组织。通过该模式,只需返回一个公有API,其他的一切都维持在私有闭包中

(1)Module模式的实现

(2)Module模式的具体使用

用Module模式来实现一个购物车,模块本身包含在basketModule的全局变量中。模块中的basket数组是私有的,因此在程序其他地方无法访问到。具体代码如下:

//Module实现购物车 var basketModule = (function () {//私有var basket = [];//存放商品function doSomethingPrivate () {// do something}//返回一个公有的对象return {//添加item到购物车addItem: function (item) {basket.push(item);},//获取购物车里item的数量getItemCount: function () {return basket.length;},//获取购物车里item的总价格getTotalMoney: function () {var itemCount = this.getItemCount();var total     = 0;for(var i = 0; i < itemCount; i ++) {total += basket[i].price;}return total;}};}) ();//basketModule 返回了一个拥有公用API的对象basketModule.addItem({item : "bread",price: 0.5});basketModule.addItem({item : "egg",price: 1.0});var totalMoney = basketModule.getTotalMoney();console.log(totalMoney);//1.5

优点:有一定的封装思想,支持私有数据
缺点:由于访问公有和私有成员的方式不同,当想改变可见性时,必须要修改每一个曾经使用过该成员的地方。(这只是其中一个缺点,但是其他缺点我还没有完全理解,欢迎交流补充)

二-2、Revealing Module模式

揭示模块模式:能够在私有范围内简单定义所有的函数和方法,并返回一个匿名对象,它拥有指向私有函数的引用。

RevealingModule模式的实现

优点:很容易在模块底部看出哪些函数和变量可以被公开访问,改善了可读性
缺点:脆弱,谨慎使用

三、Singleton(单例)模式

Singleton单例模式: 限制了类的实例化次数只能一次,在实例不存在的情况下,通过调用方法创建一个类来实现新实例的创建,若实例已经存在,则返回该对象的引用
在JavaScript中,Singleton充当共享资源命名空间,从全局命名空间中隔离出代码实现,从而为函数提供单一访问点

1、Singleton的实现

2、Singleton的使用

var singletonTest = SingletonTester.getInstance({name  : "vicky",pointX: 20
});
console.log(singletonTest);

适用性: 当类只能有一个实例而客户可以从一个众所周知的访问点访问它时。

四、Prototype(原型)模式

Prototype模式:我们可以认为其实基于原型继承的模式,可以在其中创建对象,作为其他对象的原型。

该模式与之前博文中继承里的原型继承类似,不再赘述。【JavaScript难点1】继承

五、Command(命令)模式

Command模式:旨在将方法调用/请求或操作封装到单一对象中,从而根据我们不的请求对客户进行参数化和传递可供执行的方法调用。个人理解,就是多了一个execute方法,能够按需调用。

execute()使得我们可以调用任意方法,并且可以传递参数。

六、Facade(外观)模式

Facade:尽管一个实现可能支持具有广泛行为的方法,但是却只有一个“外观”能够供公众使用。

例如,跨浏览器的添加事件处理程序,

addHandler: function (element,type,handler) {if (element.addEventListener) {element.addEventListener(type,handler,false);} else if (element.attachEvent) {element.attachEvent("on" + tye,handler);} else {element["on" + tyle] = handler;}}

我们在调用addHandler时,实际上会触发一系列的私有行为,但是我们并不知道,我们只知道 用这个方法就可以跨浏览器的添加事件处理程序,这其实就是一种Facade模式。

七、Factory(工厂)模式

Factory模式:不显式的要求使用一个构造函数,而是提供一个通用的接口来创建对iang,我们可以指定我们所希望创建的工厂对象的类型。

//工厂模式
//工厂模式可以提供一个通用的接口来创建对象,它不显式的要求使用一种构造函数//定义构造函数
function Car (options) {this.doors = options.doors || 4;this.state = options.state || "brand new";this.color = options.color || "red";
}
function Truck (options) {this.state     = options.state || "used";this.wheelSize = options.wheelSize || "large";this.color     = options.color || "blue";
}//定义工厂
function VehicleFactory () {}
VehicleFactory.prototype.vehicleClass = Car;
VehicleFactory.prototype.createVehicle = function (options) {if (options.vehicleType === "Car") {this.vehicleClass = Car;} else {this.vehicleClass = Truck;}return new this.vehicleClass(options);
};var carFactory = new VehicleFactory();
var car = carFactory.createVehicle({vehicleType: "war",color      : "black",doors      : 6
});console.log(car);

八、Mixin模式

Mixin:可以轻松被一个子类或者一组子类继承功能的类。
目的是函数复用

我们可以把Mixin看作一种通过扩展来收集功能的方式。我们定义的每个新对象都有一个原型,可以从中继承更多属性。原型可以继承与其他对象的原型,并且,它可以为任一数量的对象实例定义属性。

var Car = function (settings) {this.model = settings.model;this.color = settings.color;
};//Mixin
var Mixin = function () {};
Mixin.prototype = {driveForward: function () {console.log("drive forward");},driveBackward: function () {console.log("drive backward");}
};//通过一个方法将现有对象扩展到另一个对象上
function extend (receivingClass,givingClass) {for (var methodName in givingClass.prototype){if(! receivingClass.prototype[methodName]){receivingClass.prototype[methodName] = givingClass.prototype[methodName];}}
}
//使用
extend(Car,Mixin);//创建一个Car
var myCar = new Car( {model: "Ford",color: "red"
});myCar.driveForward();//drive forward

**优点:**Mixin有助于减少系统中的重复功能及添加函数复用

本篇博文只做了简单的介绍和梳理,相关代码已放在github上 JavaScriptDesignPatterns 。
另外 观察者模式和中介者模式有很多相似之处,将专门写博文进行学习。

【JavaScript设计模式】(一)相关推荐

  1. 《JavaScript设计模式》——11.2 一切只因跨域

    本节书摘来自异步社区<JavaScript设计模式>一书中的第11章,第11.2节,作者:张容铭著,更多章节内容可以访问云栖社区"异步社区"公众号查看 11.2 一切只 ...

  2. 《JavaScript设计模式与开发实践》模式篇(12)—— 装饰者模式

    在传统的面向对象语言中,给对象添加功能常常使用继承的方式,但是继承的方式并不灵活, 还会带来许多问题:一方面会导致超类和子类之间存在强耦合性,当超类改变时,子类也会随之 改变;另一方面,继承这种功能复 ...

  3. JavaScript设计模式与开发实践——JavaScript的多态

    "多态"一词源于希腊文polymorphism,拆开来看是poly(复数)+ morph(形态)+ ism,从字面上我们可以理解为复数形态. 多态的实际含义是:同一操作作用于不同的 ...

  4. 16种JavaScript设计模式(中)

    简介 上文中介绍了学习设计模式前需要了解的一些基础概念和js的基础模式-原型模式,没看过的同学可以点这里,本章将介绍以下几种模式 单例模式 策略模式 代理模式 迭代器模式 发布订阅模式 命令模式 组合 ...

  5. javascript 设计模式(一)

    1.为什么要深入学习Javascript? 用户对页面的美观性,易用性要求越来越高 Javascript+HTMl5+CSS3将是未来客户端技术的潮流 学好JS有助于更好学习JS库.JS框架 开发自己 ...

  6. JavaScript设计模式--简单工厂模式例子---XHR工厂

    JavaScript设计模式--简单工厂模式例子---XHR工厂 第一步,Ajax操作接口(目的是起一个接口检测作用) (1)引入接口文件 //定义一个静态方法来实现接口与实现类的直接检验 //静态方 ...

  7. JavaScript 设计模式基础(二)

    JavaScript 设计模式基础(一) 原型模式 在以类为中心的面向对象编程语言中,类和对象的关系就像铸模和铸件的关系,对象总是从类中创建.而原型编程中,类不是必须的,对象未必从类中创建而来,可以拷 ...

  8. 《JavaScript设计模式与开发实践》阅读摘要

    <JavaScript设计模式与开发实践>作者:曾探 系统的介绍了各种模式,以及js中的实现.应用,以及超大量高质量代码,绝对值得一读 面向对象的js 静态类型:编译时便已确定变量的类型 ...

  9. JS代理模式《JavaScript设计模式与开发实践》阅读笔记

    代理模式 代理模式是为一个对象提供一个代用品或占位符,以便控制对它的访问. 保护代理和虚拟代理 保护代理:当有许多需求要向某对象发出一些请求时,可以设置保护代理,通过一些条件判断对请求进行过滤. 虚拟 ...

  10. JavaScript设计模式系列四之外观模式(附案例源码)

    文章初衷 设计模式其实旨在解决语言本身存在的缺陷, 目前javaScript一些新的语法特性已经集成了一些设计模式的实现, 大家在写代码的时候,没必要为了用设计模式而去用设计模式, 那么我这边为什么还 ...

最新文章

  1. jieba分词工具的使用方法
  2. ssrf 服务器端请求伪造 简介
  3. Java反射机制——获取成员变量构造函数
  4. distributed processing(分布式处理)
  5. POI导出word带图片及本地测试没问题,在服务器上找不到模板的问题
  6. 公司电脑监控软件_公司电脑监控软件,如何限制公司电脑网络游戏
  7. Vue之webpack之Babel
  8. 软件测试---正交试验法
  9. [Shell Programmin] ZSH
  10. 如何用wps画三线图(最方便最快的方法)
  11. oracle赋权directory,ORACLE DIRECTORY目录管理步骤
  12. 从C到C++ 番外const的用法
  13. idea里面解决jsp,html,xml黄色背景的方法
  14. cpm自动SEO写文章 关键词文本生成工具3.0版本
  15. Cisco Firepower FTD HA 配置文档
  16. 人工智能中的图灵测试
  17. Camunda Workflow BPMN 入门开发实践
  18. Lifeform——站在3D虚拟数字身份与元宇宙结合的风口之上
  19. 算生日(贼快的算法)
  20. 退出 unix 命令

热门文章

  1. 数字图像处理——最大类间方差法(OTSU)图像阈值分割实例
  2. altium designer(AD13)隐藏敷铜的方法
  3. Matlab 的fspecial函数用法
  4. 浅析银行业如何做数据治理
  5. 使用Python实现电子词典
  6. 分类问题-决策树模型
  7. ENVI监督分类及精度评价
  8. opencv接受树莓派usb摄像头rtsp视频流
  9. Rplidar A1/A2使用及Hector_SLAM建图
  10. 前端微信小程序面试题总结