javascript单例模式

来源:互联网 发布:行程助手软件 编辑:程序博客网 时间:2024/06/05 05:17

参考:http://www.cnblogs.com/TomXu/archive/2012/02/20/2352817.html

单例模式在javascript中特别常用,在javascript中什么叫做单例模式?通过确保单例对象只存在一个实例,你就可以确信自己的所有的代码使用的多是同样的全局资源。

单例模式的实现:

1.直接定义全局对象

(function(){//先看一个最常用的,也是最简单的单例//例如用户登录的时候前台有一个专门的对象存储用户的信息.这个在extjs开发中很使用//放然了真正的项目数据是从后台初始化好通过ajax请求回来的var UserInfo = {name:"USPCAT.COM",code:"00101",deptName:"PD",deptCode:"PD001",getName:function(){//...return "YUNFENGCHENG"}}//这个就是一个最简单的单体模式//他用来划分命名空间,并且将一群相关的属性和方法阻止道一起,如果他可以被初始化就只能被初始化一次//我们可以用"."来访问他了alert(UserInfo.deptName);//下面来理解下"单体划分命名空间"//划分命名空间的好处在于程序员可以很清楚的知道他们调用的单体实例大概是干什么用的var comm = {};//定义单例同对象comm.userInfo = {name:"USPCAT.COM",code:"00101"}comm.funcInfo = {funcName:"PCAT2"}//在大型程序下 存在着你写的代码,有外面弄的库代码,有同事写的接口 那么命名空间很好的把它们区分开})()

2.使用立即执行的函数

   2.1 立即加载

/** * 来个复杂点单体吧,他能解决更复杂的需求 * 这个可以用到实战了 * 单体中需要局部变量和局部方法 */(function(){//模拟一个Ajaxfunction Ajax(){}Ajax.request = function(url,fn){if(true){//成功回调fn("USPCAT.COM","EXTJS4");}}//这样在用以前的方式不实行了//我们通过闭包的原理可以解决他var UserInfo = (function(){//利用Ajax来完成操作var name = "";//局部变量var code = "";//局部变量//ajaxAjax.request("www.uspcat.com",function(n,c){name = n;code = c;})//这才是真正的单体对象return {name:name,code:code}})();//试验alert(UserInfo.name)})()

    2.2 懒加载

/** * 真正的单体需要惰性加载 * 庞大的系统会在会有很多单例这样系统一上来就全部加载的方式很不是好,我们要利用惰性单体来改造他 */(function(){//模拟一个Ajaxfunction Ajax(){}Ajax.request = function(url,fn){if(true){//成功回调fn("USPCAT.COM","EXTJS4");}}//仿照java来完成var UserInfo = (function(){var userInfo = "";//私有变量function init(){//利用Ajax来完成操作var name = "";//局部变量var code = "";//局部变量//ajaxAjax.request("www.uspcat.com",function(n,c){name = n;code = c;})//这才是真正的单体对象return {name:name,code:code}}return {getInstance:function(){if(userInfo){return userInfo;}else{userInfo = init();return userInfo;}}}})();//试验alert(UserInfo.getInstance().name)})()

3.使用静态属性缓存实例

function Universe() {    // 判断是否存在实例    if (typeof Universe.instance === 'object') {        return Universe.instance;    }    // 其它内容    this.start_time = 0;    this.bang = "Big";    // 缓存    Universe.instance = this;    // 隐式返回this}// 测试var uni = new Universe();var uni2 = new Universe();console.log(uni === uni2); // true

4.使用全局变量缓存实例

var Universe;(function () {    var instance;    Universe = function Universe() {        if (instance) {            return instance;        }        instance = this;        // 其它内容        this.start_time = 0;        this.bang = "Big";    };} ());//测试代码var a = new Universe();var b = new Universe();alert(a === b); // truea.bang = "123";alert(b.bang); // 123

5.方法末尾直接重写构造函数

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.bang = "123";console.log(uni === uni2); // trueconsole.log(uni2.bang); // 123

6.先重写构造函数后再处理原型对象

function Universe() {    // 缓存实例    var instance;    // 重新构造函数    Universe = function Universe() {        return instance;    };    // 后期处理原型属性    Universe.prototype = this;    // 实例    instance = new Universe();    // 重设构造函数指针    instance.constructor = Universe;    // 其它功能    instance.start_time = 0;    instance.bang = "Big";    return instance;}// 测试var uni = new Universe();var uni2 = new Universe();console.log(uni === uni2); // true// 添加原型属性Universe.prototype.nothing = true;var uni = new Universe();Universe.prototype.everything = true;var uni2 = new Universe();console.log(uni.nothing); // trueconsole.log(uni2.nothing); // trueconsole.log(uni.everything); // trueconsole.log(uni2.everything); // trueconsole.log(uni.constructor === Universe); // true



1 0
原创粉丝点击