欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

javascript基础(二)---变量提升

程序员文章站 2022-04-04 21:53:07
...

变量提升

1. var

提升原则: 在Javascript中执行上下文中先创建变量,并初始化为 undefined, 在执行代码地方赋值

	// demo , 变量在全局环境或函数内声明均适用
	function fn(){
  		var x = 1
  		var y = 2
	}
	fn()

在执行 fn 时,JS 引擎会有以下过程(不完全):

  • 进入 fn, 为 fn 创建一个环境。
  • 找到 fn 中所有用 var 声明的变量, 在这个环境中「创建」这些变量(即 x 和 y)。
  • 将这些变量「初始化」为 undefined。
  • 开始执行代码
    x = 1 将 x 变量「赋值」为 1
    y = 2 将 y 变量「赋值」为 2
2. function

提升原则: 在Javascript执行上下文中, 在代码执行前就创建、初始化并赋值

	fn2();
	function fn2(){
  		console.log(2)
	}

JS 引擎会有一下过程:

  • 找到所有用 function 声明的变量,在环境中「创建」这些变量。
  • 将这些变量「初始化」并「赋值」为 function(){ console.log(2) }。
  • 开始执行代码 fn2()
3.let

提升原则: 在Javascript执行上下文中, 在代码执行前提升创建

{
// 例子1
  let x = 1
  x = 2
}

{} 里面JS 引擎会有以下过程:

  • 找到所有用 let 声明的变量, 在环境中「创建」这些变量
  • 在声明地方先开始执行代码(注意现在还没有初始化)
  • 执行 x = 1, 将 x 「初始化」为 1(这并不是一次赋值, 如果代码是 let x,就将 x 初始化为 undefined)
  • 执行 x = 2, 对 x 进行「赋值」
// 例子2
let x = 'global'
{
  console.log(x) // Uncaught ReferenceError: x is not defined
  let x = 1
}

原因有两个:

  • console.log(x) 中的 x 指的是{}里面的 x, 而不是全局的 x
  • 执行 log 时 x 还没「初始化」, 所以不能使用(也就是所谓的暂时死区)
// 例子3
{
  let x = x // VM112:1 Uncaught ReferenceError: Cannot access 'x' before initialization
  x = 2 // Uncaught ReferenceError: x is not defined
  let x = 3 //Uncaught SyntaxError: Identifier 'x' has already been declared
}

原因如下:

  • let x 的初始化过程失败, x 变量永远处于 created 状态, 且 x 永远处在暂时死区。
  • 无法再次对 x 进行初始化(初始化只有一次机会,而那次机会你失败了)。
4. const

提升原则: 在Javascript执行上下文中, 在代码执行前提升创建, 与let不同的是, 只有创建初始化两过程, 没有赋值过程

{
  const x = 1
}

{} 里面JS 引擎会有以下过程:

  • 找到所有用 const 声明的变量, 在环境中「创建」这些变量
  • 开始执行代码(注意现在还没有初始化)
  • 执行 x = 1, 将 x 「初始化」为 1(const 必须声明同时要初始化)
总结
  • var 的「创建」和「初始化」都被提升了。
  • function 的「创建」「初始化」和「赋值」都被提升了。
  • let 的「创建」过程被提升了,但是初始化没有提升。
  • const 的「创建」过程被提升了,但是初始化没有提升, 同时没有赋值过程。
  • let与const在 JS执行上下文中存在暂时死区, 就是不能在初始化之前,使用变量。

文章学习自: https://zhuanlan.zhihu.com/p/28140450