JavaScript 编程模式
编程模式,是源自经验和探索总结出的最佳实践方案,既有助于可读性和可维护性,也有助于提升整体性能。
行为隔离
总则:结构、样式和行为之间两两隔离。
避免在结构中使用内联事件
尽量少用
<script>标签考虑 JavaScript 被禁用的情况,添加一些替换标签
命名空间
为了减少命名冲突,优化 JavaScript 性能,尽量只定义几个全局变量,并将其他变量和方法定义为这几个变量的属性。
//定义全局变量
var MYAPP = window.MYAPP || {};
//定义属性
MYAPP.event = {};
//定义方法
MYAPP.event = {
addListener : function() {
//执行相关的逻辑操作
}
removeListener : function() {
//执行相关的逻辑操作
}
//其他方法
};
在命名空间中使用构造器函数。
MYAPP.dom = {};
MYAPP.dom.Element = function (type, prop) {
var tep = document.createElement(type);
for (var i in prop) {
tmp.setAttribute(i, prop[i]);
}
return tmp;
}
命名空间方法:
var MYAPP = window.MYAPP || {};
MYAPP.namespace = function (name) {
var parts = name.split(“.”);
var current = MYAPP;
for (var i in parts) {
if (!current[parts[i]]) {
current[parts[i]] = {};
}
current = current[parts[i]];
}
}
MYAPP.namespace(“dom.event”);
// 上述操作等价于:
var MYAPP = {
dom: {
event: {}
}
}
初始化功能
由于浏览器的不一致性,当我们使用 JavaScript 操作 DOM 或 BOM 前,通常会进行一定的功能检测。如果在运行前需要检测的功能较多,那么就会严重影响脚本的执行速度。对于这个问题,可以通过初始化功能解决,即在脚本加载后,立即对重要的函数执行功能检测。如此,后续就无需检测功能,可以直接执行相关的函数。
var MYAPP = window.MYAPP || {};
MYAPP.event = {
addListener: null,
removeListener: null
};
// 初始化功能演示如下:
if (typeof window.addEventListener === ‘function’) {
MYAPP.event.addListener = function (el, type, fn) {
el.addEventListener(type, fn, false);
};
MYAPP.event.removeListener = function (el, type, fn) {
el.removeEventListener(type, fn, false);
};
} else if (typeof document.attachEvent === “function”) {
MYAPP.event.addListener = function (el, type, fn) {
el.attachEvent(“on” + type, fn);
};
MYAPP.event.removeListener = function (el, type, fn) {
el.detachEvent(“on” + type, fn);
};
} else {
MYAPP.event.addListener = function (el, type, fn) {
el[“on” + type] = fn;
};
MYAPP.event.removeListener = function (el, type, fn) {
el[“on” + type] = null;
};
}
延迟定义
延迟定义,恰巧与初始化模式的思想相反。对于那些不一定会被调用的函数,可以让其被调用时再初始化,并且只进行一次初始化。
var MYAPP = window.MYAPP || {};
MYAPP.event = {
addListener: function(el, type, fn) {
if (typeof window.addEventListener === ‘function’) {
MYAPP.event.addListener = function (el, type, fn) {
el.addEventListener(type, fn, false);
};
} else if (typeof document.attachEvent === “function”) {
MYAPP.event.addListener = function (el, type, fn) {
el.attachEvent(“on” + type, fn);
};
} else {
MYAPP.event.addListener = function (el, type, fn) {
el[“on” + type] = fn;
};
}
MYAPP.event.addListener(el, type, fn);
}
};
这个地方我需要修改一下,使用可以重写自己的函数。
配置对象
配置对象模式,适用于向函数中传递多个参数。简单的说,就是将参数集合放入一个对象中,将对象传给参数,这个对象甚至可以是一个 JSON 文件。当参数量较少时,就像是传统的传参,当参数集庞大时,就如同传递环境配置变量。将变量和函数解耦,是非常不错的实践:
无需考虑参数的顺序
可以忽略某些参数
具有更好的可读性和可维护性
var MYAPP = window.MYAPP || {};
MYAPP.dom = {};
MYAPP.dom.Button = function(text, conf) {
var type = conf.type || “submit”;
var color = conf.color || “red”
}
// 使用方式
var conf = {
type: “reset”,
color: “green”
};
new MYAPP.dom.Button(“Reset”, conf);
私有变量和方法
与 C++、JAVA 不同,JavaScript 中并没有控制访问权限的修饰符,但我们可以使用局部变量和函数来实现类似的权限控制。
var MYAPP = window.MYAPP || {};
MYAPP.dom = {};
MYAPP.dom.Button = function (text, conf) {
var styles = {
color: “black”
}
function setStyles() {
for (var i in styles) {
b.style[i] = conf[i] || styles[i];
}
}
conf = conf || {};
var b = document.createElement(“input”);
b.type = conf[“type”] || “submit”;
b.value = text;
setStyles();
return b;
}
在这里,styles 是一个私有属性,而 setStyle() 则是一个私有方法。构造器可以在内部调用它们(它们也可以访问构造器中的任何对象),但它们不能被外部代码所调用。
特权函数
在上例中,我们可以为 b 添加一个 getDefaults() 方法,返回 styles 对象,从而实现对内部属性或方法的访问,这个 getDefaults() 就是一种特权函数。
私有函数的公有化
为了防止外部修改,将函数设为私有,有时候又想外部可以访问到,所以有需要设为公有。解决方案是,使用公有变量引用私有函数,即可将其公有化。
var MYAPP = window.MYAPP || {};
MYAPP.dom = {};
MYAPP.dom.Button = (function () {
var _setStyle = {};
var _getStyle = ();
return {
setStyle: _setStyle,
getStyle: _getStyle,
yetAnother: _setStyle
};
})();
自执行的函数
使用立即执行的匿名函数,同样可以保证全局命名空间不会受到污染。这种函数的所有变量都是局部的,并在函数返回时被销毁(非闭包)。
适合于执行一次性的初始化任务。
(function(){
//编写逻辑操作代码
})()
链式调用
链式调用,是一种便捷的调用方式。其实现本质是使用一致的上下文对象,并在链式方法间传递这个对象。这种灵活的调用方式也是 jQuery 的一大特色。
JSON
JSON 是一种轻量级的数据交换格式。由于它本身就是由类似 JavaScript 的对象和数组标记的数据构成的,所以解析起来非常方便。
说道解析,我们可以使用 JavaScript 的 eval() 方法转换;但是由于 eval() 本身的缺陷,这件事还是使用更安全的方法吧,比如 JavaScript 的某些库(http://json.org):
var obj = JSON.parse(xhr.respnseText);
JavaScript 编程模式的更多相关文章
- Javascript编程模式(JavaScript Programming Patterns)Part 1.(初级篇)
JavaScript 为网站添加状态,这些状态可能是校验或者更复杂的行为像拖拽终止功能或者是异步的请求webserver (aka Ajax). 在过去的那些年里, JavaScript librar ...
- Javascript编程模式(JavaScript Programming Patterns)Part 2.(高级篇)
模块编程模式的启示(Revealing Module Pattern) 客户端对象(Custom Objects) 懒函数定义(Lazy Function Definition) Christian ...
- javascript常见编程模式举例
近期买到手了一本<javascript框架设计>,具体介绍开发js框架所用到的知识.初读一点,乐帝脆弱的理论修养就暴露无遗了,所以专门加强理论修养,重看javascript编程模式的举例. ...
- javascript编程单线程之同步模式
javascript编程单线程之同步模式 主流的js 环境都是单线程吗模式执行js 代码, js采用为单线程的原因与最开始设计初衷有关,最早是运行在浏览器端的脚本语言,目的是为了实现页面上的动态交互, ...
- Javascript原型模式总结梳理
在大多数面向对象语言中,对象总是由类中实例化而来,类和对象的关系就像模具跟模件一样.Javascript中没有类的概念,就算ES6中引入的class也不过是一种语法糖,本质上还是利用原型实现.在原型编 ...
- javascript编程的最佳实践推荐
推荐的javascript编程的最佳实践,摘要记录在这里: 可维护的代码保证代码的性能部署代码 1 可维护的代码1.1什么是维护的代码:可理解性——其他人可以接手代码并理解它的意图和一般途径,而无需原 ...
- JQuery日记6.5 Javascript异步模式(一)
理解力JQuery前实现异步队列,有必要理解javascript异步模式. Javascript异步其实并不严重格异步感,js使某些片段异步方式在将来运行,流不必等待继续向下进行. 在多线程的语言中最 ...
- 【HANA系列】SAP HANA XS使用JavaScript编程详解
公众号:SAP Technical 本文作者:matinal 原文出处:http://www.cnblogs.com/SAPmatinal/ 原文链接:[HANA系列]SAP HANA XS使用Jav ...
- 学习现代 JavaScript 编程的最佳教程
天天编码 , 版权所有丨本文标题:0.0 学习现代 JavaScript 编程的最佳教程 转载请保留页面地址:http://www.tiantianbianma.com/the-modern-java ...
随机推荐
- 在ie和chrome浏览器中滚动条样式的设置
1.IE下设置滚动条样式的属性 scrollbar-arrow-color: color; /*三角箭头的颜色*/scrollbar-face-color: color; /*立体滚动条的颜色(包括箭 ...
- qt 如何给图元安装一个场景事件过滤器?
void QGraphicsItem::installSceneEventFilter(QGraphicsItem *filterItem) class LabCrossEvent : public ...
- Python3.6全栈开发实例[023]
23.税务部门征收所得税. 规定如下: (1)收入在2000以下的. 免征. (2)收入在2000-4000的, 超过2000部分要征收3%的税. (3)收入在4000-6000的, 超过4000部分 ...
- win7安装laravel
使用Packagist 镜像 建立一个composer.json文件,内容如下: { "name": "laravel/laravel", "desc ...
- 剑指offer 面试61题
面试61题: 题目:LL今天心情特别好,因为他去买了一副扑克牌,发现里面居然有2个大王,2个小王(一副牌原本是54张^_^)...他随机从中抽出了5张牌,想测测自己的手气,看看能不能抽到顺子,如果抽到 ...
- 正则表达式test match exec search
(1)((2))(3) $1 是第一个括号 $2 是第二个括号 $3 是第二个括号中的括号 $4 是第三个括号 http://www.jb51.net/article/28007. ...
- CSS清除浮动使父级元素展开的三个方法
点评:一个没有设置高度的容器div内如果存在浮动元素(即使用了属性float:left或者float:right),那么该父级元素会无法展开,下面举个例子为大家详细介绍下,希望对大家有所帮助 一个没有 ...
- 'substring(from:)' is deprecated: Please use String slicing subscript with a 'partial range from' operator.
let newStr = String(str[..<index]) // = str.substring(to: index) In Swift 3 let newStr = String(s ...
- python中的值传递和引用传递
Python中的变量是没有类型的,我们可以把它看做一个(*void)类型的指针,变量是可以指向任何对象的,而对象才是有类型的. Python中的对象有可变对象(number,string,tuple等 ...
- 【TopCoder】SRM160 DIV1总结
做了两道题之后才发现做的是DIV1,不是DIV2,DIV1的第二道题是DIV1的第三道题,果断决定第3题就不看了=.= 250分题:给定一个时间起点8:00 AM DAY 1,再给出一组时间终点,格式 ...