JavaScript设计模式之单体模式全面解析


Posted in Javascript onSeptember 09, 2016

单体是一个用来划分命名空间并将一些相关的属性与方法组织在一起的对象,如果她可以被实例化的话,那她只能被实例化一次(她只能嫁一次,不能二婚)。

单体模式是javascript里面最基本但也是最有用的模式之一。

特点:

1. 可以用来划分命名空间,从而清除全局变量所带来的危险或影响。

2. 利用分支技术来来封装浏览器之间的差异。

3. 可以把代码组织的更为一体,便于阅读和维护。

单体模式的基本写法:

/* 最基本的单体模式 */ 
var her = {
name: 'Anna',
sex: 'women',
say: function(){
// 一些处理逻辑......
},
doing: function(){
// 另一些处理函数......
} 
}

1. 划分命名空间:

var box = {
width: 0,
height: 0,
getArea: function(){
return this.width * this.width; // js中对象成的访问必须是显示的,即this是不能省略的
},
init: function(w, h){
// width = w;
// height = h;这种方式相当于定义了两个全局变量,(没加var声明的变量为全局变量)
// 并不是对对象width和height的赋值
// 下面是正确的
this.width = w;
this.height = h;
}
} //box划分了一个命名空间,命名空间里的变量只在空间里有效

上面的单体中的所有的成员以及方法都是公有的(public),也就是在单体的外部可以对她们进行任意的改动(但不能访问其中的局部变量),那为什么说单体提供了一个命名空间呢?

别急,我们接着往下看:

var box = {
width:0,
height:0,//单体的变量
getArea:function(){
return width * height;// width,height其实并不是单体的变量,而是在init中定义的全局变量
}
init:function(w,h){
width = w;
height = h;
}
}// init中width,height其实并不是单体的变量
window.onload = function(){
var init = box.getArea();
alert(init);
}

由于没有对init中的width,height进行初始化,所以会报错,这样改一下:

var box = {
width:0,
height:0,
getArea:function(){
return width * height;
},
init:function(w,h){
width = w;
height = h;
}
}
window.onload = function(){
width = 0;
height = 0;
//or box.init(0,0);
var init = box.getArea();
alert(init);
}

发现可以了,由于init和 getArea所用的width和height并不是归单体所有的变量,而是一个全局变量,所以我们可以在单体外面进行随意调用而不受影响、

var box = {
width: 0,
height: 0,
getArea: function(){
return width * height;//js中对象成的访问必须是显示的,即this是不能省略的
},
init:function(w,h){
width = w;
height = h;
}
}//这里的width,height其实并不是单体的对象
window.onload = function(){
width = 0;
height = 0;
var width = box.getArea();
alert(width);
}

这样写又会报错了,可见我们以上的方式对于全局变量并没有建立起一个命名空间,全局变量为我们带来了危险。所以最上面的写法是对的,我们来验证一下:

var box = {
width: 2,
height: 2,
getArea: function(){
return this.width * this.height;/ /js中对象成的访问必须是显示的,即this是不能省略的
},
init:function(w,h){
this.width = w;
this.height = h;
}
}
window.onload = function(){
width = 0; // 不会影响单体中的局部变量也就是命名空间
height = 0; // 不会影响单体中的局部变量也就是命名空间
var width = box.getArea();
alert(width);
}

可见在window.onload中的width 和height已经没有干扰了,因为单体为单体中的width和height建立了一个命名空间。

2. 成员的属性:

虽然在javascript中没有这么严格的面向对象(oop),但是我们可以借助闭包来进行一个模仿,毕竟有的变量设为public是很不好的。

var her = (function(){
var name = 'Anna';
var sex = 'women';
return {
getArea: function(){
return name + 'is a' + sex;
},
init:function(b){
name = b;
}
}
})();
window.onload = function(){
her.name = 'Jock'; // 无法访问
alert(ger.getArea());
her.init('Lous');
alert(her.getArea());
}

私有变量、方法是只读的,公有变量、方法是可读可写的。

访问:

对于私有成员,直接访问即可,前面不用加任何修饰,
对于公有的访问在单体作用域内前面要加上“this.”,在单体作用域外前面要加上“her.”(单体名字.)

3.利用分支技术来来封装浏览器之间的差异

注意的地方:

a. 一定要用闭包,实现即时绑定

b. 每个分支之间用分号隔开

c. 最后返回的是分支的名字

d. 调用的时候用单体名+分支的方法名;

// 利用单体的分支技术来定义XHR(XMLHttpRequest)对象,必须要用闭包才可以实现
var XHR = (function(){
//The three branches
var standard = {
cXHR:function(){
return new XMLHttpRequest();
} 
};
var activeXNew = {
cXHR:function(){
return new ActiveXObject('Msxml2.XMLHttp');
} 
};
var activeXOld = {
cXHR:function(){
return new ActiveXObject('Microsoft.XMLHttp');
} 
};
//To assign(分配) the branch, try each method;return whatever doesn't fail
var testObject;
try{
testObject = standard.cXHR();
return standard;// return this branch if no error was thrown 
}catch(e){
try{
testObject = activeXNew.cXHR();
return activeXNew;
}catch(e){
try{
testObject = activeXOld.cXHR();
return activeXOld;
}catch(e){
throw new Error('Create the XMLHttpRequestObject failed!'); 
}
}
}
})();
window.onload = function(){
alert(XHR.cXHR());
}

以上所述是小编给大家介绍的JavaScript设计模式之单体模式全面解析,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对三水点靠木网站的支持!

Javascript 相关文章推荐
网页防止tab键的使用快速解决方法
Nov 07 Javascript
解决JQeury显示内容没有边距内容紧挨着浏览器边线
Dec 20 Javascript
jquery制作select列表双向选择示例代码
Sep 02 Javascript
Jquery中$.post和$.ajax的用法小结
Apr 28 Javascript
wap手机端解决返回上一页的js实例
Dec 08 Javascript
微信小程序图表插件(wx-charts)实例代码
Jan 17 Javascript
Bootstrap进度条实现代码解析
Mar 07 Javascript
JavaScript实现职责链模式概述
Jan 25 Javascript
jQuery实现点击旋转,再点击恢复初始状态动画效果示例
Dec 11 jQuery
JS实现数组深拷贝的方法分析
Mar 06 Javascript
vue实现微信二次分享以及自定义分享的示例
Mar 20 Javascript
基于JavaScript实现省市联动效果
Jun 22 Javascript
jQuery实现的超链接提示效果示例【附demo源码下载】
Sep 09 #Javascript
全面解析Bootstrap表单样式的使用
Sep 09 #Javascript
jQuery+ajax读取并解析XML文件的方法
Sep 09 #Javascript
JS与jQuery实现隔行变色的方法
Sep 09 #Javascript
jQuery层次选择器用法示例
Sep 09 #Javascript
jQuery基本过滤选择器用法示例
Sep 09 #Javascript
jQuery可见性过滤选择器用法示例
Sep 09 #Javascript
You might like
曾在DC漫画界反派角色扮演的演员,谁才是你心目中的小丑之王?
2020/04/09 欧美动漫
PHP中数组的三种排序方法分享
2012/05/07 PHP
php利用新浪接口查询ip获取地理位置示例
2014/01/20 PHP
PHP 中 Orientation 属性判断上传图片是否需要旋转
2015/10/16 PHP
ThinkPHP5框架缓存查询操作分析
2018/05/30 PHP
Laravel Eloquent ORM 多条件查询的例子
2019/10/10 PHP
firefox浏览器下javascript 拖动层效果与原理分析代码
2007/12/04 Javascript
基于jquery的让页面控件不可用的实现代码
2010/04/27 Javascript
jquery 查找select ,并触发事件的实现代码
2011/03/30 Javascript
js替换字符串的所有示例代码
2013/07/23 Javascript
js 动态为textbox添加下拉框数据源的方法
2014/04/24 Javascript
javascript圆盘抽奖程序实现原理和完整代码例子
2014/06/03 Javascript
JavaScript编写推箱子游戏
2015/07/07 Javascript
jquery实现Li滚动时滚动条自动添加样式的方法
2015/08/10 Javascript
javascript实现图片延迟加载方法汇总(三种方法)
2015/08/27 Javascript
基于insertBefore制作简单的循环插空效果
2015/09/21 Javascript
JavaScript数组方法大全(推荐)
2016/07/05 Javascript
angular使用post、get向后台传参的问题实例
2017/05/27 Javascript
AngularJS ionic手势事件的使用总结
2017/08/09 Javascript
详解react-native WebView 返回处理(非回调方法可解决)
2018/02/27 Javascript
微信小程序+云开发实现欢迎登录注册
2019/05/24 Javascript
vue中使用[provide/inject]实现页面reload的方法
2019/09/30 Javascript
javascript前端实现多视频上传
2020/12/13 Javascript
基于vue+echarts数据可视化大屏展示的实现
2020/12/25 Vue.js
[50:11]2018DOTA2亚洲邀请赛 4.7总决赛 LGD vs Mineski 第三场
2018/04/09 DOTA
python开发之thread线程基础实例入门
2015/11/11 Python
python扫描proxy并获取可用代理ip的实例
2017/08/07 Python
Flask数据库迁移简单介绍
2017/10/24 Python
pytorch 自定义卷积核进行卷积操作方式
2019/12/30 Python
Python: tkinter窗口屏幕居中,设置窗口最大,最小尺寸实例
2020/03/04 Python
Window系统下Python如何安装OpenCV库
2020/03/05 Python
Python3操作YAML文件格式方法解析
2020/04/10 Python
为你的html5网页添加音效示例
2014/04/03 HTML / CSS
N.Peal官网:来自伦敦的高档羊绒品牌
2018/10/29 全球购物
办理信用卡工作证明
2014/01/11 职场文书
办公室主任主任岗位责任制
2014/02/11 职场文书