单例模式(Singleton),整个运行期间只会被初始化一次。该模式简单易懂,运用也很广泛。可以用它来聚合公共的方法,形成一个工具类,对外提供api。
1. 单例模式的基本结构
var Singleton = {
attr1: 'test1',
attr2: 10,
method: function(){
...
},
...
}
这就是一个单例对象,Singleton是全局变量,js载入时被初始化一次。
jquery就是一个很大的单例 (function(){var jquery=(function(){})();window.jQuery = window.$ = jQuery;})(window);
2. 拥有私有变量的单例模式
jascript的对象在运行期间是可以直接修改的,也没有其他面向对象语言的private等关键字。一些方法又不想被外面直接调用或者修改。
2.1 私有方法命名方法 _getName,方法名称前加下划线,约定此类方法或变量为私有
var Singleton = {
_value: '23s',
_stringSplit: function(str, delimeter){...},
}
2.2 闭包
var Singleton = (function(){
var titileId = "rules";
function closePanel(id){
....
}
return {
publicAttr: 1,
publicMethod: function(){
closePanel(this.publicAttr);
}
}
})();
titleId属性和closePanle因为在闭包内部,所有成了私有变量,外部不可访问和修改。
titleId属性声明的时候必须加var关键字,不然就变成一个全局变量。
3. lazy初始化
由于单例对象一直存在内存之中,如果比较大的实例,一开始就初始化,代价比较高,可以等到需要的时候再初始化
var Singleton = (function(){
var uniqueInstance;
function constructor(){
var privateAttr = "";
function privateMethod(){}
return {}
}
return {
getInstance: function(){
if(!uniqueInstance){
uniqueInstance = new constructor();
}
return uniqueInstance;
}
}
})();
4. 命名空间
一个页面会载入多个js,全局变量和方法会有冲突或覆盖的风险。把变量和方法都放到一个单例对象下面,避免冲突。
var MyNamespace = {
}
一个创建命名空间的方法
function createNameSpace(spaceStr){
var space = spaceStr.split(".");
var parent = window, name = "";
for(var i = 0; i < space.length; i++){
name = space[i];
parent = parent[name] = parent[name] || {};
}
}