js性能相关

一、注意作用域

  避免全局查找:全局变量的查找肯定比局部的开销更大,因为要涉及到作用域链上的查找。

  解决办法:若需要对document的引用,创建一个指向document的局部变量。

  例如:

  

1  function updateUI(){
2     var imgs=document.getElementByTagsName('img');
3     for(var i=0,len=imgs.length;i<len;i++){
4     imgs[i].title=document.title+i;
5     }  
6 }    
7 //如果有很多图片的话就要引用全局变量document很多遍,每次都进行作用域链的查找.性能肯定好不了。
8 //就像你要在一个大房间里找一个小东西一样,每次都要从头到尾找一遍。太辛苦。

 

 //既然找的很辛苦,那么,我先把它的具体位置写在一张纸条上,放入一个
 2 //离我最近盒子里去,下次找的话,在盒子里面取就
 3 //好了(按照位置直接去找,不用走弯路)
 4 function updateUI(){
 5     var doc=document;//纸条入盒子
 6     var imgs=doc.getElementByTagsName('img');
 7     for(var i=0,len=imgs.length;i<len;i++){
 8     imgs[i].title=document.title+i;
 9     }  
10 }
11 //现在就节省了好多麻烦(优化性能)

  

  避免with语句:原理跟上面差不多,with会增加执行代码中作用域链的长度。额外的作用域链的查找,速度肯定就慢了。

function updatebody(){
  with(document.body){
    innerHTML='helllo world!';
 }
}
//全局查找
function(){
 var body=document.body;
 body.innerHTML='hello world!'
}
//储存在局部变量中,避免了全局查找

 

二、选择正确方法

  避免不必要的属性查找

  这里正确的方法可以说是解决问题的算法和方法。

   一般算法越复杂,执行的时间越长。列举几中算法:

    

O(1) 常数 不管值多少,执行的时间是一定的:一般是简单的值和储存在变量中的值
O(log n) 对数 总执行时间和值得数量有关
O(n) 线性 总执行时间和值得数量直接相关:遍历数组中的所有元素
O(n2) 平方 总执行时间和值得数量有关,每个值至少获取n次

   注意:获取常量和访问数组元素属于O(1),效率比获取对象属性(需要先在原型链中对拥有该名称的属性进行查找)要高。

    多次用到同一个属性时,存在局部变量中。

    优化循环

    1 减值迭代:从最大值开始,而不是0

  2 简化终止条件:每次循环都要计算终止条件,避免O(n)操作

    3 简化循环体:确保没有可以容易移除循环的密集计算

  4 使用后测试循环:避免最初终值条件的计算。(这种情况要保证至少有一个处理的值)

    如果这些都做到了,就只能优化process()函数了

 展开循环

  process(values[0]);

      process(values[1]);

      process(values[2]);

这样避免了建立循环和处理终值条件的额外开销,是代码运行更快。

如果迭代次数不能定用Duff装置技术

避免双重解释

 容易产生的地方:eval()函数 Function()构造函数 setTimeout() 都会造成双重解析,而实例化一个新的解析器开销很大。

 解决方法:尽量避免用eval()函数

     函数写成一般的函数,函数字表达式,函数声明。

     setTime 中传入函数作为第一个参数而不是包含js代码的字符串。

其他需要注意的地方

1 原生方法较快(用c/c++语言写出来的比js快)

2 Switch语句较快(可以代替大量使用if-else的时候)

3 按位运算符较快

 

三、最小化语句数

  单语句多操作比多语句但操作快,这句话的意思是,能写成一个语句就不要写成两个语句。比如说:

    1 多变量声明的时候

    

var i=5;
var color='purple';
var values=[1,2,3];
//可以写成
var i=5,color='purple',values[1,2,3];

 

 

 

   2 插入迭代

 

var name=values[i];
i++;
//换成这样
var name=values[i++];

 

      3 定义数组和对象时尽量使用字面量。这样可以消除不必要的语句。(代码就不展示了,脑补吧。)

 

 

四、优化DOM交互

     1 最小化现场更新

         浏览器需要计算尺寸进行更新,所以越少越好

var list=document.getElementById('list');
 var item,i;
 for(i=10;i>=0;i--){
     item=document.createElement('li');
     list.appendChild(item);
     item.appendChild(document.creatTextnode('item'+i));
 }
 //可以通过创建片段来减少现场更新
var list=document.getElementById('list');
fragment=document.createDocumentFragment();
 var item,i;
 for(i=10;i>=0;i--){
     item=document.createElement('li');
     fragment.appendChild(item);
     item.appendChild(document.creatTextnode('item'+i));
 }
 list.appendChild(fragment);

  2 需要大量创建DOM节点的时候,用innerHTML比createElement()和appendChild()快。

 

var list=document.getElementById('list');
html='';
for(i=10,i>=0;i--){
    html+='<li>item'+i+'</li>';   
}
list.innerHTML='html';

3 使用事件代理(前面有一篇说过这个)

4 注意HTMLcollection

   要尽量减少HTMLcollection的访问

var imags=document.getElementsByTagName('img');
 for(var i=0,len=imags.length;i<len;i++){
    //处理
 }
//将HTMLcollection的length属性存入一个局部变量,以后访问这个局部变量就可以了

这里说一下会产生HTNLcollection的地方

1 getElemenstByTagName()

2 childNodes

3 attributes

4 document.forms  document.images

 

 

 

终于总结完了(js高级程序设计)。。。以前写代码还真的没有考虑这么多,以后要把这些思想融入自己的代码中,养成一个好的习惯。

 


 

posted @ 2015-05-17 19:56  mikou  阅读(269)  评论(0编辑  收藏  举报