js性能优化小结

避免全局查找
浏览器访问局部变量的速度要比访问全局变量的速度更快,变量在作用域链中一层一层查找需要消耗时间。
 1   // 不推荐
 2   function fn(){
 3     document.getElementById('id1');
 4     document.getElementById('id2');
 5   }
 6 
 7   // 推荐
 8   function fn(){
 9     var doc = document;
10     doc.getElementById('id1');
11     doc.getElementById('id2');
12   }
13   // 推荐
14   !function fn(doc){
15     doc.getElementById('id1');
16     doc.getElementById('id2');
17   }(document);

 

类似eval的问题
js中的eval、setTimeout、setInterval、new Function()操作都能将字符串当作js代码来执行,在此过程中代码执行效率非常底下,应当避免使用。推荐使用匿名函数或传递函数引用。
 1   // 不推荐使用eval
 2 
 3   // setTimeout、setInterval、new Function建议直接传入匿名函数或函数引用
 4   setTimeout('alert(1)', 1000); // 不推荐
 5   setInterval('alert(1)', 1000); // 不推荐
 6   var oFn = new Function('alert(1)'); // 不推荐
 7 
 8   // 推荐
 9   setTimeout(function(){
10     alert(1);
11   }, 1000);
12   setTimeout(fn, 1000);
13 
14   setInterval(function(){
15     alert(1);
16   }, 1000);
17   //setInterval(fn, 1000);
18 
19   var oFn = new Function(function(){
20     alert(1);
21   });
22   var oFn = new Function(fn);
23 
24   function fn(){
25     alert(1);
26   }

 

定时器
当不断间隔一段时间运行代码时,应当使用setInterval,而不要通过setTimeout来实现,因为开启一个定时器都会初始化一次,采用setTimeout是通过不断初始化定时器来实现的。
 1   var i = 0,
 2     timer = null;
 3 
 4   // 不推荐
 5   function fnTimeout(){
 6     if(i < 10){
 7       setTimeout(fnTimeout, 1000); // 不断初始化
 8     }
 9     console.log(i++);
10   }
11   fnTimeout();
12 
13   // 推荐
14   function fnInterval(){
15     if(i >= 10){
16       clearInterval(timer);
17       timer = null;
18     }
19     console.log(i++);
20   }
21   setInterval(fnInterval, 1000); // 初始化一次

 

多个字符串连接
如果需要将多个字符串连接起来,要少使用+=,最好使用数据的jolin方法。
 1   var a = 'a',
 2     b = 'b',
 3     c = 'c',
 4     s = '',
 5     arr = [];
 6 
 7   // 不推荐
 8   s += a;
 9   s += b;
10   s += c;
11 
12   // 推荐
13   s = a + b + c;
14 
15   // 最佳
16   arr.push(a);
17   arr.push(b);
18   arr.push(c);
19   s = arr.join('');

 

类型转换
将数字转换为字符串使用"" + 数字 ;
字符串转数字:1*字符串;
任何内型转布尔:!!变量;
变量声明使用单var
变量声明都采用单var形式,可以减少代码执行时间,变量声明比较统一。
 1   // 不推荐
 2   var a = 'a';
 3   var b = 'b';
 4   var c = 'c';
 5   var s = '';
 6   var arr = [];
 7 
 8   // 推荐
 9   var a = 'a',
10     b = 'b',
11     c = 'c',
12     s = '',
13     arr = [];

 

自增自减放入表达式中
1   // 不推荐
2   var i = 0,
3     b = i;
4   i++;
5 
6   // 推荐
7   var i = 0,
8     b = i++;

 

使用对象和数组字面量
1   // 不推荐
2   var arr = new Array,
3     obj = new Object,
4     re = new RegExp('a');
5   
6   // 推荐
7   var arr = [],
8     obj = {},
9     re = /a/;

 

闭包中不再使用的变量的释放
闭包中的变量如果有其他函数使用了,那么该变量一直会留在内存中,另外DOM的引用会消耗很大的内存,因此应该及时释放闭包中不再引用的变量。
 1   // 不推荐
 2   var fn = !function(doc){
 3     var obj = {name: 'hum'},
 4       arr = [1, 2],
 5       oDom = doc.getElementById('id');
 6 
 7     // ......
 8 
 9     return function(){
10       console.log(obj.name);
11     }
12   }(document);
13 
14   // 推荐
15   var fn = !function(doc){
16     var obj = {name: 'hum'},
17       arr = [1, 2],
18       oDom = doc.getElementById('id');
19 
20     // ......
21 
22     arr = doc = oDom = null; // 释放
23 
24     return function(){
25       console.log(obj.name);
26     }
27   }(document);

 

减少reflow
在css规范中有一个渲染对象的概念,通常用盒子来表示。mozilla通过一个叫frame的对象来操作盒子。
reflow:加载DOM树、创建或更新frame结构的响应 的过程。减少reflow的方法:
1、将元素删除,完成修改后还原
2、将元素display等于none,完成修改后还原
3、修改多个样式时用类代替对此style操作
4、添加大量元素到页面使用documentFragment
事件委托
将子元素的事件都注册到父元素或更高的元素上,不用为每个子节点注册事件监听。
DOM删除
删除DOM节点时,一定要删除DOM上绑定的事件,否则无法回收,占用内存。
减少DOM集合的访问
通过js获取集合的情况:
1、getElementsByTagName
2、childNodes
3、attributes
4、document.forms  document.images
...
缩短否定操作
尽量使用逻辑非来进行条件判断,而减少使用等于null或等于false
posted @ 2015-03-05 13:31  tyxloveyfq  阅读(479)  评论(0编辑  收藏  举报