有效提高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 相关文章推荐
使两个iframe的高度与内容自适应,且相等
Nov 20 Javascript
javascript 词法作用域和闭包分析说明
Aug 12 Javascript
jquery中动态效果小结
Dec 16 Javascript
css3元素简单的闪烁效果实现(html5 jquery)
Dec 28 Javascript
jquery中的常用事件bind、hover、toggle等示例介绍
Jul 21 Javascript
JQuery控制radio选中和不选中方法总结
Apr 15 Javascript
JavaScript中数据结构与算法(五):经典KMP算法
Jun 19 Javascript
javascript数据结构之双链表插入排序实例详解
Nov 25 Javascript
bootstrap multiselect下拉列表功能
Aug 22 Javascript
js禁止浏览器页面后退功能的实例(推荐)
Sep 01 Javascript
Angular4学习教程之HTML属性绑定的方法
Jan 04 Javascript
JS实现公告上线滚动效果
Jan 10 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
Php Mssql操作简单封装支持存储过程
2009/12/11 PHP
PHP strncasecmp字符串比较的小技巧
2011/01/04 PHP
php魔术方法与魔术变量、内置方法与内置变量的深入分析
2013/06/03 PHP
php动态生成函数示例
2014/03/21 PHP
Yii实现MySQL多数据库和读写分离实例分析
2014/12/03 PHP
Javascript 继承机制实例
2009/08/12 Javascript
js简单的表格添加行和删除行操作示例
2014/03/31 Javascript
在JavaScript的AngularJS库中进行单元测试的方法
2015/06/23 Javascript
js window对象属性和方法相关资料整理
2015/11/11 Javascript
在AngularJS框架中处理数据建模的方式解析
2016/03/05 Javascript
基于JavaScript实现回到页面顶部动画代码
2016/05/24 Javascript
js移动焦点到最后位置的简单方法
2016/11/25 Javascript
微信页面倒计时代码(解决safari不兼容date的问题)
2016/12/13 Javascript
javascript兼容性(实例讲解)
2017/08/15 Javascript
ng-alain表单使用方式详解
2018/07/10 Javascript
vue的style绑定background-image的方式和其他变量数据的区别详解
2018/09/03 Javascript
用图片替换checkbox原始样式并实现同样的功能
2018/11/15 Javascript
详解Python中表达式i += x与i = i + x是否等价
2017/02/08 Python
python 脚本生成随机 字母 + 数字密码功能
2018/05/26 Python
Python中最大递归深度值的探讨
2019/03/05 Python
django 中的聚合函数,分组函数,F 查询,Q查询
2019/07/25 Python
python2 对excel表格操作完整示例
2020/02/23 Python
python 使用cx-freeze打包程序的实现
2020/03/14 Python
Python+PyQt5+MySQL实现天气管理系统
2020/06/16 Python
中国电子产品外贸网站:MiniIntheBox
2017/02/06 全球购物
雅高酒店中国:Accorhotels.com China
2018/03/26 全球购物
英国豪华家具和经典家居饰品购物网站:OKA
2020/06/05 全球购物
慰问敬老院活动总结
2014/04/26 职场文书
单位实习工作证明怎么写
2014/11/02 职场文书
2014年企业党支部工作总结
2014/12/04 职场文书
2015政治思想表现评语
2015/03/25 职场文书
装配车间主任岗位职责
2015/04/08 职场文书
民政局未婚证明
2015/06/15 职场文书
2016中秋节广告语
2016/01/28 职场文书
Python还能这么玩之用Python修改了班花的开机密码
2021/06/04 Python
一文简单了解MySQL前缀索引
2022/04/03 MySQL