有效提高JavaScript执行效率的几点知识


Posted in Javascript onJanuary 31, 2015

为了提供新鲜、别致的用户体验,很多网站都会使用 JavaScript 来改善设计、验证表单、检查浏览器,以及Ajax请求,cookie操作等等,实现无刷新动态效果 。但是,要将大量内容在浏览器呈现,如果处理不好,网站性能将会急剧下降。所以我们有必要了解下,如何提高JavaScript的执行效率。

JavaScript 函数

在JavaScript 中,函数在使用前会预编译。尽管有些时候下可以使用字符串代替函数,但是每次执行这段JavaScript 代码时都会重新解析,影响性能。

1、eval例子

eval('output=(input * input)');

// 建议改成:

eval(new function() { output=(input * input)});

2、setTimeout例子

setTimeout("alert(1)", 1000);

// 建议改成:

setTimeout(function(){alert(1)}, 1000);

使用函数代替字符串作参数确保新方法中的代码能被 JavaScript 编译器优化。

JavaScript作用域

JavaScript作用域链中的每个作用域都包含几个变量。理解作用域链很重要,这样才能利用它。

var localVar = "global"; //全局变量
function test() {
  var localVar = "local"; //局部变量
  //局部变量

  alert(localVar);
  //全局变量

  alert(this.localVar);
  //查找document在局部变量找不到,就查找全局变量

  var pageName = document.getElementById("pageName"); 

}

使用局部变量比使用全局变量快得多,因为在作用域链中越远,解析越慢。下图显示了作用域链结构:

有效提高JavaScript执行效率的几点知识

如果代码中有 with 或 try-catch 语句,作用域链会更复杂,如下图:

有效提高JavaScript执行效率的几点知识

JavaScript字符串

JavaScript中一个非常影响性能的函数是字符串连接,一般情况都是使用 + 号来实现拼接字符串。但是早期浏览器没有对这样的连接方式做优化,导致在连续创建和销毁字符串严重降低JavaScript执行效率。

var txt = "hello" + " " + "world";

建议改成:

var o = [];

o.push("hello");

o.push(" ");

o.push("world");

var txt = o.join();

我们再简单封装一下:

function StringBuffer(str) {

    var arr = [];

    arr.push(str || "");

    this.append = function(str) {

        arr.push(str);

        return this;

    };

    this.toString = function() {

        return arr.join("");

    };

};

然后这样子调用:

var txt = new StringBuffer();

txt.append("Hello");

txt.append(" ");

txt.append("World");

alert(txt.toString());

JavaScript DOM操作

HTML Document Object Model (DOM) 定义了访问和操作 HTML 文档的标准方法。它将 HTML 文档表示成节点树,其中包含元素、属性和文本内容。通过使用 HTML DOM,JavaScript 能访问 HTML 文档中所有节点并操作它们。

DOM重绘

每次修改到页面的DOM对象,都涉及到DOM重绘,浏览器都会重新渲染页面。所以降低DOM对象的修改次数,可以有效地提高JavaScript 的性能。

for (var i = 0; i < 1000; i++ ) {

  var elmt = document.createElement('p');

  elmt.innerHTML = i;

  document.body.appendChild(elmt);

}

建议改成:

var html = [];

for (var i = 0; i < 1000; i++) {

  html.push('<p>' + i + '</p>');

}

document.body.innerHTML = html.join('');

DOM访问

通过DOM可以访问到HTML文档中的每个节点。每次调用getElementById()、getElementsByTagName()等方法,都会重新查找并访问节点。所以将查找到的DOM节点缓存一下,也可以提高JavaScript 的性能。

document.getElementById("p2").style.color = "blue";

document.getElementById("p2").style.fontFamily = "Arial";

document.getElementById("p2").style.fontSize = "larger";

建议改成:

var elmt = document.getElementById("p2");

elmt.style.color = "blue";

elmt.style.fontFamily = "Arial";

elmt.style.fontSize = "larger";

DOM遍历

DOM遍历子元素通常都是按索引循环读取下一个子元素,在早期浏览器下这种读取方式执行效率很低,利用nextSibling方式可以提高js遍历DOM的效率。

var html = [];

var x = document.getElementsByTagName("p");//所有节点

for (var i = 0; i < x.length; i++)  {

  //todo

}

建议改成:

var html = [];

var x = document.getElementById("div");//上级节点

var node = x.firstChild;

while(node != null){

  //todo

  node = node.nextSibling;

}

JavaScript 内存释放

在web应用中,随着DOM对象数量的增加,内存消耗会越来越大。所以应当及时释放对象的引用,让浏览器能够回收这些内存。

释放DOM占用的内存

document.getElementById("test").innerHTML = "";

将DOM元素的innerHTML设置为空字符串,可以释放其子元素占用的内存。

释放javascript对象

//对象:

obj = null

//对象属性:

delete obj.property

//数组元素:

arr.splice(0,3);//删除前3个元素
Javascript 相关文章推荐
javascript学习笔记(九) js对象 设计模式
Jun 19 Javascript
利用js实现选项卡的特别效果的实例
Mar 03 Javascript
jquery分页插件AmSetPager(自写)
Apr 15 Javascript
js动态修改input输入框的type属性(实现方法解析)
Nov 13 Javascript
jquery显示loading图片直到网页加载完成的方法
Jun 25 Javascript
js简单判断移动端系统的方法
Feb 25 Javascript
微信小程序 wx.request(OBJECT)发起请求详解
Oct 13 Javascript
layui前段框架日期控件使用方法详解
May 19 Javascript
JS实现简单的选择题测评系统代码思路详解(demo)
Sep 03 Javascript
react-native中ListView组件点击跳转的方法示例
Sep 30 Javascript
vue-router之nuxt动态路由设置的两种方法小结
Sep 26 Javascript
JavaScript Math对象和调试程序的方法分析
May 13 Javascript
JavaScript日期时间与时间戳的转换函数分享
Jan 31 #Javascript
JavaScript监听和禁用浏览器回车事件实例
Jan 31 #Javascript
JavaScript编程中容易出BUG的几点小知识
Jan 31 #Javascript
JavaScript实现的双向跨域插件分享
Jan 31 #Javascript
JavaScript判断变量是否为空的自定义函数分享
Jan 31 #Javascript
分享两个手机访问pc网站自动跳转手机端网站代码
Dec 24 #Javascript
js判断登录与否并确定跳转页面的方法
Jan 30 #Javascript
You might like
第五节--克隆
2006/11/16 PHP
深入php数据采集的详解
2013/06/02 PHP
php自定义urlencode,urldecode函数实例
2015/03/24 PHP
SpringMVC框架下JQuery传递并解析Json格式的数据是如何实现的
2015/12/10 Javascript
javascript时间排序算法实现活动秒杀倒计时效果
2021/01/28 Javascript
详解Nodejs基于mongoose模块的增删改查的操作
2016/12/21 NodeJs
详解vue slot插槽的使用方法
2017/06/13 Javascript
layui获取选中行数据的实例讲解
2018/08/19 Javascript
javascript原型链学习记录之继承实现方式分析
2019/05/01 Javascript
实用的Vue开发技巧
2019/05/30 Javascript
在vue中对数组值变化的监听与重新响应渲染操作
2020/07/17 Javascript
vue封装自定义指令之动态显示title操作(溢出显示,不溢出不显示)
2020/11/12 Javascript
用Python登录Gmail并发送Gmail邮件的教程
2015/04/17 Python
python获取当前时间对应unix时间戳的方法
2015/05/15 Python
Python编程之属性和方法实例详解
2015/05/19 Python
Python常用知识点汇总
2016/05/08 Python
python数据类型_字符串常用操作(详解)
2017/05/30 Python
在scrapy中使用phantomJS实现异步爬取的方法
2018/12/17 Python
基于python-opencv3的图像显示和保存操作
2019/06/27 Python
Django ORM 常用字段与不常用字段汇总
2019/08/09 Python
详解Python 字符串相似性的几种度量方法
2019/08/29 Python
关于Python turtle库使用时坐标的确定方法
2020/03/19 Python
基于html5实现的图片墙效果
2014/10/16 HTML / CSS
详解通过focusout事件解决IOS键盘收起时界面不归位的问题
2019/07/18 HTML / CSS
美国祛痘、抗衰老药妆品牌:Murad
2016/08/27 全球购物
Mytheresa美国官网:德国知名的女性奢侈品电商
2017/05/27 全球购物
解释下列WebService名词:WSDL、SOAP、UDDI
2012/06/22 面试题
医学专业毕业生推荐信
2013/11/14 职场文书
中学家长会邀请函
2014/01/17 职场文书
二年级语文教学反思
2014/02/02 职场文书
反对形式主义、官僚主义、享乐主义和奢靡之风整改措施
2014/09/17 职场文书
重阳节演讲稿:尊敬帮助老人 弘扬传统美德
2014/09/25 职场文书
个人租房协议书
2014/11/28 职场文书
档案工作个人总结
2015/03/03 职场文书
幼儿园春季开学通知
2015/07/16 职场文书
十大冰系宝可梦排名,颜值最高的阿罗拉九尾,第三使用率第一
2022/03/18 日漫