javaScript几种设计模式之一——单体模式

javaScript是一种弱类型、动态的、基于原型的语言,这种语言特性使得它非常容易、

甚至是普通的方式实现其中的一些模式。

单体模式的思想在于保证一个特定类仅有一个实例。这就意味着当您第二次使用同一个

类创建新对象的时候,应该得到与第一次所创建对象完全相同对象。

在javaScript中没有类,只有对象。当您创建一个新对象时,实际上没有其他对象与其

类似,因此新对象已经是单体了。使用对象字面量创建一个简单的对象也是一个单体的

例子。

var obj ={

myprop:’my value’

};

在javaScript中,对象之间永远不会完全相等,除非他们是同一个对象,因此即使创建

一个具有完全相同成员的同类对象,它也不会与第一个对象完全相同。

var obj2 = {

myprop:’mu value’

};

obj === obj2 //false

obj == obj2 //false

因此,可以认为每次在使用对象字面量创建对象的时候,实际上就正在创建一个单体,

并且并不涉及任何特殊语法。

javaScript中并没有类,因此对单体咬文嚼字的定义严格说来并没有意义。但是

javaScript中具有new语法可使用构造函数来创建对象,而且有时可能需要使用这种语法

的单体实现。这种思想在于当使用一个构造函数以new操作符来创建多个对象时,应该仅

获得指向完全相同的对象的新指针。

下面的代码显示了其预期行为

var uni = new Universe();

var uni2 = new Universe();

uni === uni2; //true

在上面的例子中,uni对象仅在第一次调用构造函数时被创建。在第二次及以后的创建时

将会返回同一个uni对象。这就是为什么uni===uni2,因为它们本质上是指向同一个对象

的两个引用。那么如何在javaScript中实现这种模式呢?

需要Universe构造函数缓存该对象实例this,以便当第二次调用该构造函数时能够创建并

返回同一个对象。有多种选择可以实现这一目标:

1.可以使用全局变量来存储该实例,但是并不推荐使用这种方法,因为在一般原则下,

全局变量有部分缺点。此外,任何人都能覆盖该全局变量。

  1. 可以在构造函数的静态属性中缓存该实例,javaScript中的函数也是对象,因此它们

也可以有属性。可以使用类似Universe.instance的属性并将实例缓存在该属性重工,这

是一种很好的实现方法,这种解决方案唯一的缺点在于instance属性是公开可访问的属

性,在外部代码中可能会修改该属性,以至于会丢失了该实例。

如例子:

function Universe(){

//判断是否有实例

if(typeof Universe.instance === ‘object’){

return Universe.instance;

}

//正常进行

this.start_time = 0;

this.bang = “Big”;

//缓存

Universe.instance = this;

}

//

var uni = new Universe();

var uni2 = new Universe();

uni === uni2; //true

这种方法是一个非常直接的解决方法,其唯一的缺点在于其instance属性是公开的,虽

然其他代码不太可能会无意中修改该属性,但是仍然存在这种可能性。

3.可以将该实例包装在闭包中。这样可以保证该实例的私有属性并且保证该实例不会被

构造函数之外的代码所修改,缺点就是带来了额外的闭包开销。

如下面例子:

function Universe(){

//缓存实例

var instance = this;

//正常进行

this.start_time=0;

this.bang = “big”;

//重写该构造函数

Universe = function(){

return instance;

};

}

var uni = new Universe();

var uni2 = new Universe();

uni === uni2; //true

当第一次调用原始构造函数时,它像往常一样返回this,然后,在第二次、第三次调用

时,将执行重写构造函数。该重写构造函数通过闭包访问了私有instance 变量,并且仅

简单返回了该instance.在重写构造函数会丢失所有在初始定义和重定义时刻之间添加到

它里面的属性。在这列的特定情况下,任何添加到universe的原型中对象都不会存在指

向由原始实现所创建实例的活动链接。

另外一种方法是将构造函数和实例包装在即时函数中。在第一次调用构造函数时,它会

创建一个对象,并且似的私有instance指向该对象,从第二次调用之后,该构造函数仅

返回该私有变量,通过这个新的实现方式,前面所有代码片段的测试也都会按照预期运

行。

var Universe;

(function (){

var instance;

Universe = function Unvierse(){

if(instance){

return instance;

}

instance = this;

//所有功能

this.start_time = 0;

this.bang = “Big”;

};

}());

时间: 2024-10-10 12:33:23

javaScript几种设计模式之一——单体模式的相关文章

Java经典23种设计模式之创造型模式(二)

本文记录5种创造型模式的剩下两种:建造者模式(Builder).原型模式(PROTOTYPE). 一.建造者模式(别名:生成者模式) 将复杂对象的构建和它的表示分离,使得同样的构建过程可以创建不同的表示.一个完整的建造者模式包含以下几个概念: 1.产品类 Product public class Person { private String head; private String body; private String foot; public String getHead() { ret

Spring 实现两种设计模式:工厂模式和单态模式

在Spring 中大量使用的以下两种设计模式:工厂模式和单态模式. 工厂模式可将Java 对象的调用者从被调用者的实现逻辑中分离出来,调用者只需关心被调用者必须满足的规则(接口) ,而不必关心实例的具体实现过程.这是面向接口编程的优势,能提高程序的解耦,避免所有的类以硬编码方式耦合在一起. 如果所有的类直接耦合,极易形成"骨牌效应",假如B 类调用了A 类,一旦A 类需要修改,则B 类也需要修改:假如C 类调用了B 类,则C 类也需要修改......依次类推,从而导致整个系统都需要改写

javascript设计模式之单体模式

一入前端深似海,刚入前端,以为前端只是div+css布局外加jquery操作DOM树辣么简单.伴随着对前端学习的深入,发现前端也是博大精深,而且懂得越多,才发现自己越无知,所以一定不能停下脚步的学习.原来前端也有设计模式,那么开始了解吧! 今天来学最简单的单体模式,其实就是简单的Object扩展 var calcYourShengXiao={ solar : ["甲","乙","丙","丁","午",&qu

javascript --- 设计模式之单体模式

单体是一个用来划分命名空间并将一些相关的属性与方法组织在一起的对象,如果她可以被实例化的话,那她只能被实例化一次(她只能嫁一次,不能二婚). 单体模式是javascript里面最基本但也是最有用的模式之一. 特点:1. 可以用来划分命名空间,从而清除全局变量所带来的危险或影响. 2. 利用分支技术来来封装浏览器之间的差异.   3. 可以把代码组织的更为一体,便于阅读和维护. 单体模式的基本写法: /* 最基本的单体模式 */ var her = { name: 'Anna', sex: 'wo

23种设计模式(19)---Command模式

命令(Command)模式属于对象的行为模式[GOF95].命令模式又称为行动(Action)模式或交易(Transaction)模式.命令模式把一个请求或者操作封装到一个对象中.命令模式允许系统使用不同的请求把客户端参数化,对请求排队或者记录请求日志,可以提供命令的撤销和恢复功能. 命令模式是对命令的封装.命令模式把发出命令的责任和执行命令的责任分割开,委派给不同的对象. 每一个命令都是一个操作:请求的一方发出请求要求执行一个操作:接收的一方收到请求,并执行操作.命令模式允许请求的一方和接收的

JAVA开发的23种设计模式之 --- 桥接模式

桥接模式 概述:将抽象部分与他的实现部分分离,这样抽象化与实现化解耦,使他们可以独立的变化.如何实现解耦的呢,就是通过提供抽象化和实现化之间的桥接结构.    应用场景        实现系统可能有多个角度分类,每一种角度都可能变化.    解释:桥接模式将继承模式转化成关联关系,他降低了类与类之间的耦合度,减少了系统中类的数量,也减少了代码量.    理解抽象化,实现化,解耦        抽象化:将复杂物体的一个或几个共同的特性抽出去而只注意其他特性的行动或过程.在java面向对象中抽象化就

23种设计模式之代理模式(Proxy)

代理模式是一种对象结构型模式,可为某个对象提供一个代理,并由代理对象控制对原对象的引用.代理模式能够协调调用者和被调用者,能够在一定程度上降低系统的耦合度,其缺点是请求的处理速度会变慢,并且实现代理模式需要额外的工作. 优点: 1)远程代理可以隐藏对象位于不同的地址空间的事实. 2)虚拟代理可以执行优化操作,例如根据需要创建一个对象. 使用场景:需要比简单的指针更灵活.更全面的对象引用. Proxy 模式

23种设计模式之原型模式(Prototype)

在系统开发过程中,有时候有些对象需要被频繁创建,原型模式通过给出一个原型对象来指明所要创建的对象的类型,然后通过复制这个原型对象的办法,创建出更多同类型的对象.原型模式是一种对象创建型模式,用原型实例制定创建对象的种类,并且通过复制这些原型创建新的对象.原型模式又可分为两种:浅克隆和深克隆.浅克隆仅仅复制所考虑的对象,而不复制它所引用的对象,也就是其中的成员对象并不复制:深克隆除了对象本身被复制外,对象包含的引用也被复制,即成员对象也被复制. 优点: 1)可以在运行时添加或删除产品. 2)通过改

javascript --- 设计模式之单体模式(二)

在JavaScript里,实现单例的方式有很多种,其中最简单的一个方式是使用对象字面量的方法,其字面量里可以包含大量的属性和方法: var her = { property1: 'someing', property2: 'someing else', method1: function(){ console.log('hello, Javascript'); } } 如果以后要扩展该对象,你可以添加自己的私有成员和方法,然后使用闭包在其内部封装这些变量和函数声明.只暴露你想暴露的public成