Javascript 代码优化

客户端的脚本可以使你的应用变得动态和生动,但是浏览器对于JavaScript的解释可能会导致效率的底下,而且随着客户端本身的不同也会导致性能的不同。我们整理了一些建议和最好的实践来优化你的Javascript 代码。

###定义class的方法

下面这个例子是低效的,每一次实例化baz.Bar,都会创建一个新foo的闭包函数。

1
2
3
4
5
6
baz.Bar = function() {  
// constructor body
this.foo = function() {
// method body
};
}

比较好的方法是

1
2
3
4
5
6
7
baz.Bar = function() {
// constructor body
};

baz.Bar.prototype.foo = function() {
// method body
};

这种方式,无论创建多少个baz.Bar的示例,都只会创建一个foo函数,同时也没有闭包函数产生。

###初始化实例变量
Place instance variable declaration/initialization on the prototype for instance variables with value type (rather than reference type) initialization values (i.e. values of type number, Boolean, null, undefined, or string).这个可以避免每次构建函数被调用时不必要地每次都运行初始化代码(但是如果你的实例变量是依赖于构建函数的传入参数,或者依赖于构建时的一些状态则不适用于该建议)

例子

1
2
3
4
5
6
foo.Bar = function() {  
this.prop1_ = 4;
this.prop2_ = true;
this.prop3_ = [];
this.prop4_ = 'blah';
};

应该改为下面这种形式

1
2
3
4
5
6
7
8
9
foo.Bar = function() {
this.prop3_ = [];
};

foo.Bar.prototype.prop1_ = 4;

foo.Bar.prototype.prop2_ = true;

foo.Bar.prototype.prop4_ = 'blah';

###避免落入闭包的陷进

闭包是Javascript中一个很强大也很有用的一个特性;同时,它也有一些缺点:

  • 闭包是最常见的导致内存泄漏的原因
  • 创建一个闭包比起不使用闭包来创建一个内在的函数来说慢得多,和重用一个静态的函数来比要更加慢。如下例子
1
2
3
4
function setupAlertTimeout() {
var msg = 'Message to alert';
window.setTimeout(function() { alert(msg); }, 100);
}

较快的:

1
2
3
4
5
6
function setupAlertTimeout() {
window.setTimeout(function() {
var msg = 'Message to alert';
alert(msg);
}, 100);
}

更快的

1
2
3
4
5
6
7
8
function alertMsg() {
var msg = 'Message to alert';
alert(msg);
}

function setupAlertTimeout() {
window.setTimeout(alertMsg, 100);
}

  • 闭包会增加作用域的长度。当浏览器解析属性的时候,作用域的每一级都必须被查询。如下例子
1
2
3
4
5
6
7
8
9
10
11
12
13
14
var a = 'a';

function createFunctionWithClosure() {
var b = 'b';
return function () {
var c = 'c';
a;
b;
c;
};
}

var f = createFunctionWithClosure();
f();

f被执行,引用c快于b,快于a
在ie中使用闭包的信息可以浏览IE+JScript Performance Recommendations Part 3: JavaScript Code inefficiencies

###避免使用with
在你的代码中要避免视同with。它的性能很差,因为它会修改作用域链,使得其他的作用域连中查找变量变得困难。网站应用中最常见的内存泄漏是因为JavaScript脚本引擎和浏览器的C ++对象实现DOM一件的循环引用(例如:between the JavaScript script engine and Internet Explorer’s COM infrastructure, or between the JavaScript engine and Firefox XPCOM infrastructure)

###避免浏览器内存泄漏

在web应用中内存泄漏是一个很常见的问题,它会导致巨大的性能问题。当你的网站应用导致浏览器使用的的内存增加,会影响到用户的系统的其他部分变得缓慢。

这里有一些经验的法则来避免内存泄漏:

把事件处理绑定在事件管理系统上

最常见的循环引用类型就是 [ DOM element –> event handler –> closure scope –> DOM ],为了避免这种问题,应该选择一个经过良好测试的事件管理系统来绑定事件处理,例如Google doctype,Dojo或者Jquery。

未完

原文链接