var let const
Babel转码器,将es6 => es5
var
用于定义变量,存在变量提升
let
用于定义变量,不存在变量提升
let的一些特性
let不存在变量提升
conslog.log(a);
let a = 10; //报错
同一个作用域内不能重复定义一个名称
var a = 1;
let a = 1;//报错
a = 1;
let a = 1;//报错
存在块级作用域
出现{ }就是有块级作用域
function test() {
let a = 10;
if (true) {
let a = 1;
}
console.log(a);//10
}
暂时性死区
function f3(i) {
let i = 10;
console.log(i);
}
f3(33);//报错,同名
函数参数,会先赋值
var i = 33;
let i = 33;
let a = b, b = 3;
consloe.log(a,b);//报错 b未定义
小案例
var arr = [];
for (var i = 0;i < 5;i++) {
arr[i] = function() {
console.log(i)
}
}
arr[0]();
...
arr[4](); //全是5
//解析:
//for循环中
for() {
var i = 0;
arr[i] = function() {
console.log(i)
}
i < 5
i++;
....
arr[i] = function() {
console.log(i)
}
i < 5
i++;
//直到 i = 5,此过程中函数并没有调用,因此最后i=5
然后再调用函数,显而易见i的值是5
//如果将var换成let,则不会出现这样的情况,因为let存在块级作用域,输出的结果是正常值
}
const
声明一个只读的常量,常量的值不能改变,const也拥有let的三大特性
const x = 1;
x = 2;//报错 不能修改
const x; //报错,const变量一旦声明,必须要付初值
const的坑
首先我们回顾一下,变量的知识点,数据分为简单类型和引用类型,简单类型存储在栈里面,而引用类型则在栈中存储一个指针,指向堆中存储的数据,因此我们const一个obj,只是保证栈中的数据不变,也就是地址(指针)不变,而在堆中的值是可以改变的
const obj = {id: 1};
obj.id = 2; //正确