从var到let和const
var变量提升
在函数作用域和全局作用域中,var声明的变量都被当成在作用域顶部声明的变量。
块级声明
- 函数内部
- 块中({ }之间)
let声明
- 作用:把作用域限制在代码块中。
禁止重声明
作用域中已存在某个标识符(var、let、const),再let声明就会报错。
const声明
const声明变量
定义后不可更改,通过const声明的变量必须进行初始化。
const声明对象
不允许修改对象,但可以修改对象的属性值。
临时死区TDZ
js引擎在扫描代码发现变量声明时,要么提升至作用域顶部(遇到var声明),要么将声明放到TDZ中。访问TDZ中的变量会触发运行时错误。执行过变量声明语句后,变量才会从TDZ中移出,然后才能正常访问。
循环中的块作用域绑定
1 | for ( var i = 0; i< 10; i++ ) { |
在循环结束后仍能访问 i = 10
1 | for ( let i = 0; i< 10; i++ ) { |
循环结束后,i无法访问,跑出错误
循环中的函数
预期输出0~9
1 | var funcs = [] |
因为共享变量i
调用函数表达式IIFE
1 | var funcs = [] |
IIFE为每个变量i都创建了一个副本并存储为变量value,这个变量的值就是相应迭代创建的函数所用的值。
闭包 闭包概念参考
循环中的let声明
每次迭代循环都会创建一个新变量,并以之前迭代中同名变量的值将其初始化。
1 | var funcs = [] |
for-in与for一样
循环中的const声明
for循环中,试图修改i,但i是常量,会报错。在for-in和for-of中使用和let一致,每次迭代不会修改已有绑定,会创建一个新绑定,不会报错。
for、forEach 、for in、for of 循环的区别
全局块作用域绑定
var会创建一个新的全局变量作为全局对象(window对象)的属性。var可能会无意覆盖一个已存在的全局属性。
用let和const不会覆盖全局变量,只能遮盖。