Bootstrap

前端基础之ES6

ES6

ES6简介

在这里插入图片描述
ES6实际上是一个泛指,泛指ES2015及后续版本

为什么使用ES6?

每一次标准的诞生都意味着语言的完善,功能的加强。JavaScript语言本身也有一些令人不满意的地方。

  • 变量提升特性增加了程序运行时的不可预测性
  • 语法过于松散,当实现相同的功能时,不同的人可能会写出不同的代码

变量let

let

ES6中新增的用于声明变量的关键字,ES6之前只有全局作用域和局部作用域,在之后呢才有了块级作用域

let声明的变量只在所处于的块级有效,块级作用域就是一对大括号里的作用域,块级作用域的好处是:(1)能够防止内层变量覆盖外层变量(2)防止循环变量变成全局变量

<script>
    if(true){
        let a= 10;
    }
    console.log(a); // a is not defined
</script>

*注意:*使用let关键字声明的变量才具有块级作用域。使用var声明的变量不具有块级作用域特性。

//防止循环变量变成全局变量
for (var i = 0; i < 2; i++) {
}
console.log(i);// 2 
// 如果改为let则 log打印不出来
不存在变量提升
// 使用let关键字声明的变量没有变量提升
console.log(a);
// let a = 100;//a is not defined(报错)
// var a = 100;// undefined(直接打印输出undefined)
其实在这里实际的执行顺序为:
var a;
console.log(a);
let a = 100;
a= 100;// 所以这里会打印出来undefined
暂时性死区

在块级作用域内,使用let关键字声明的变量会被整体绑定在块级区域,不再受外部代码影响

// 使用let关键字声明的变量具有暂时性死区的特性
var tmp = 123;
if (true) {
    console.log(tmp); //因为使用了let,所以死区特性,就算外面声明了tmp的全局变量,在这里输出tmp也会报错未定义
    let tmp = 111;
}
// 因此只要使用了let,就会和这个块级作用域整体绑定,使用时和外部无关系
let经典面试题

在这里插入图片描述
由于i为全局变量,在函数内部没有定义i的代码,所以匿名函数在执行时是找不到i值的,根据作用域链查找原则,要向上一层作用域链查找i的值,也就是循环创建时的变量i,由于函数调用时,循环早已经结束了,所以i的值是循环条件不满足的时候的值:也就是2。由于数组中存储的两个函数在执行时输出的都是全局变量i,都是2,在arr[0]和arr[1]调用时,i为使循环终止的值即2,所以不管中括号里的数字为几,结果都是arr[2]的值

简单来说
此题的关键点在于变量i是全局的,函数执行时输出的都是全局作用域下的i值。

在这里插入图片描述
将上述代码中的var关键字改为let关键字:
执行函数时,依旧找不到i的定义,所以向上一级进行查找,找到用let定义的i,因为是let定义的,所以是处在块级作用域中,而块级作用域之间不会彼此影响,函数输出时自己作用域下i的值。

常量const

const

作用:声明常量,常量就是指(内存地址)不能变化的量

具有块级作用域
if (true) {
    const a = 10;
}
console.log(a); // a is not defined
// 使用const关键字声明的变量具有块级作用域
if (true) {
    const a = 10;
    if (true) {
        const a = 20;
        console.log(a);//20 因为具有块级作用域,所以对大括号外的区域是没有影响的
    }
    console.log(a); // 10
}
console.log(a);// a is not defined
<

悦读

道可道,非常道;名可名,非常名。 无名,天地之始,有名,万物之母。 故常无欲,以观其妙,常有欲,以观其徼。 此两者,同出而异名,同谓之玄,玄之又玄,众妙之门。

;