ES6深入理解之“let”能替代”var“吗?


Posted in Javascript onJune 28, 2017

前言

我已经使用ES2015(ES6)的语法编写JavaScript程序很久了,并且喜欢上它提供的新特性带来的优雅和简洁。我最习惯的就是不再使用var,而是let/const。我想当然的以为let仅仅是var的替代者,而事实上let还为我们提供了更加精细的作用域。

我大多数时候使用的变量都是用const来声明,因为如果尝试对使用const声明的变量进行修改,将会报错。这可以避免不小心将一个不该修改的常量值修改。但是,我们还是需要可以声明可以被修改的变量,比如在循环里面的计数器,我们需要不断地对改变了加1。可是为什么我们使用let而不是var呢?

最简单的答案就是let提供块作用域(block-scoping),这会比var提供的以函数为作用域有更加精细化的控制。为了便于理解,我来用一个经典的前端工程师面试的问题来描述两者的区别。

问题: 在下面的例子中,请说出控制台的打印结果。

var callbacks = [];
(function() {
 for (var i = 0; i < 5; i++) {
 callbacks.push( function() { return i; } );
 }
})();
console.log(callbacks.map( function(cb) { return cb(); } ));

我们将for循环执行五次,每次将一个函数push到callbacks数组中。最后callbacks数组里面的每一个函数的执行结果打印出来。

一个新手工程师经过深思熟虑可能会回答[0, 1 , 2, 3, 4], 然而却掉入了JavaScript的”hoisting陷阱”。

只有当你理解了hoisting, 才能给出正确的答案[5, 5, 5, 5, 5]。

var callbacks = [];
(function() {
 var i;
 for (i = 0; i < 5; i++) {
 callbacks.push( function() { return i; } );
 }
})();
console.log(callbacks.map( function(cb) { return cb(); } ));

注意:上面的代码,JavaScript将变量提升到函数定义的顶部,经过整个for循环,callbacks里面存储的5个函数指向的同一个变量i的值已经是5。所以最终打印出来的值都为5。

在以前要通过各种奇淫技巧来解决这个问题,并成功返回[0, 1, 2, 3, 4], 现在我们有了let,就可以很简单解决问题:

var callbacks = [];
(function() {
 for (let i = 0; i < 5; i++) {
 callbacks.push( function() { return i; } );
 }
})();
console.log(callbacks.map( function(cb) { return cb(); } ));

因为let拥有块作用域,所以使用let声明的变量i不会被提升到函数顶部,i的作用域在for循环, 就会每次循环有独立的值。

那我们是不是应该不要使用var了呢?如果你想要一个变量拥有函数作用域,var还是很有用的。

读者提到的两个问题:

1、const声明的变量不是完全不可更改。比如:

const myNotQuiteImmutableObject = {
 thisCanBeChanged: "not immutable"
};
myNotQuiteImmutableObject.thisCanBeChanged = "see I changed it.";

但是,使用const声明可以阻止一些基本的更改,比如:

const immutableString = "you can't change me";
immutableString = "D'OH!"; // error

如果你想要完全的不可更改,可以使用Facebook提供的Immutable库。

2、老版本的浏览器不支持let。不仅如此,而且有些最新的浏览器也还没有支持let。我们可以使用Babel来避免这个问题,Babel允许你使用所有最新的JavaScript功能,然后将其翻译到甚至IE8都能支持的代码。

原文: Why You Shouldn't Use ‘var' Anymore

译者: Fundebug

为了保证可读性,本文采用意译而非直译。

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作能带来一定的帮助,如果有疑问大家可以留言交流,谢谢大家对三水点靠木的支持。

Javascript 相关文章推荐
style、 currentStyle、 runtimeStyle区别分析
Aug 01 Javascript
ajax更新数据后,jquery、jq失效问题
Mar 16 Javascript
深入理解JavaScript系列(3) 全面解析Module模式
Jan 15 Javascript
JS增加行复制行删除行的实现代码
Nov 09 Javascript
jQuery插件制作的实例教程
May 16 Javascript
jQuery数组处理函数整理
Aug 03 Javascript
JQuery Ajax WebService传递参数的简单实例
Nov 02 Javascript
微信小程序之蓝牙的链接
Sep 26 Javascript
详解webpack-dev-server使用方法
Sep 14 Javascript
小程序实现锚点滑动效果
Sep 23 Javascript
vue从后台渲染文章列表以及根据id跳转文章详情详解
Dec 14 Vue.js
vue-router懒加载的3种方式汇总
Feb 28 Vue.js
jQuery、layer实现弹出层的打开、关闭功能
Jun 28 #jQuery
AngularJS实现单一页面内设置跳转路由的方法
Jun 28 #Javascript
JavaScript中常见的八个陷阱总结
Jun 28 #Javascript
通过构造函数实例化对象的方法
Jun 28 #Javascript
JS之if语句对接事件动作逻辑(详解)
Jun 28 #Javascript
CSS3+JavaScript实现翻页幻灯片效果
Jun 28 #Javascript
Node.js 8 中的重要新特性
Jun 28 #Javascript
You might like
PHP中file_put_contents追加和换行的实现方法
2017/04/01 PHP
php实现头像上传预览功能
2017/04/27 PHP
JavaScript 对象成员的可见性说明
2009/10/16 Javascript
解决jquery插件冲突的问题
2014/01/23 Javascript
js的正则test,match,exec详细解析
2014/01/29 Javascript
jquery判断浏览器后退时候弹出消息的方法
2014/08/11 Javascript
jQuery验证插件validation使用指南
2015/04/21 Javascript
jQuery+HTML5实现图片上传前预览效果
2015/08/20 Javascript
JS实现IE状态栏文字缩放效果代码
2015/10/24 Javascript
jquery获取点击控件的绝对位置简单实例
2016/10/13 Javascript
进阶之初探nodeJS
2017/01/24 NodeJs
Vue.js进阶知识点总结
2018/04/01 Javascript
node 使用 async 控制并发的方法
2018/05/07 Javascript
vant IndexBar实现的城市列表的示例代码
2019/11/20 Javascript
在vue中使用Base64转码的案例
2020/08/07 Javascript
[36:13]Mineski vs iG 2018国际邀请赛小组赛BO2 第一场 8.16
2018/08/17 DOTA
django用户注册、登录、注销和用户扩展的示例
2018/03/19 Python
python之文件读取一行一行的方法
2018/07/12 Python
python样条插值的实现代码
2018/12/17 Python
python基础教程之while循环
2019/08/14 Python
Python整数与Numpy数据溢出问题解决
2019/09/11 Python
基于YUV 数据格式详解及python实现方式
2019/12/09 Python
Django实现celery定时任务过程解析
2020/04/21 Python
keras 两种训练模型方式详解fit和fit_generator(节省内存)
2020/07/03 Python
DRF框架API版本管理实现方法解析
2020/08/21 Python
Born鞋子官网:Born Shoes
2017/04/06 全球购物
预订奥兰多和佛罗里达州公园门票:FloridaTix
2018/01/03 全球购物
应届护士推荐信
2013/11/16 职场文书
幼儿园园长岗位职责
2013/11/26 职场文书
绩效考核实施方案
2014/03/18 职场文书
《秋游》教学反思
2014/04/24 职场文书
农村门前三包责任书
2014/07/25 职场文书
Python中for后接else的语法使用
2021/05/18 Python
阿里云日志过滤器配置日志服务
2022/04/09 Servers
oracle数据库去除重复数据
2022/05/20 Oracle
css样式important规则的正确使用方式
2022/06/10 HTML / CSS