var let const 的区别以及var let const练习题

作用域

在介绍let 和const 和 var 之前,我们先了解一下作用域,作用域在ES6之前,只用全局作用域和函数作用域,用var 声明的,在ES6 的时候,增加了以let 和const 声明的块级作用域

全局作用域

在全局作用域范围内可用,在页面关闭之后进行销毁

函数作用域

在函数内部定义 只在函数内部可以使用,在函数执行完毕之后进行销毁

块级作用域

块级作用域是ES6新增的,块级作用域是定义在大括号{}且只有let和const 声明的变量才是块级作用域在{}内使用

var let const 区别

1,var 存在变量提升(创建和初始化都提前了),let 和 const 提升了一部分(创建提升了),但是因为暂时性死区(变量没有初始化),不能在声明之前使用
2,var 可以在同一作用域重复声明变量,但是let 和 const 在同一作用域不能同时声明一个变量
3,var 只用全局作用域和函数作用域,const 和 let 多一个块级作用域
4,const声明的常量,定义的时候必须赋值,且声明之后不能修改,如果是复杂变量可以修改里面的属性值, var 和 let 可以先声明再赋值
全局下let和const 声明的变量不会作为window 对象的属性,单纯就是声明一个全局的块级变量,全局下var 声明的变量是作用域window对象属性的

变量提升的原理

js 引擎的工作方式是先解析代码,获取所有的变量,然后再运行,也就是,有预处理和执行两个阶段,var 声明的变量,在预处理的时候,会创建变量,并赋值为undefined,function 定义的函数,会将整个函数提升

var let const 练习题

这道题是我第一次面试时遇到的题,

var a =1
fun()
function fun(){
console.log(a)
if(!a){
var a=3
}
console.log(a)
}
console.log(a)

undefined,3,1 ,
这里考察的是变量提升,块级作用域以及函数作用域,块级作用域,var 声明的定义是没有块级作用域的概念的,所以在函数内第一行 a 存在变量提升,并为undefined,然后执行里面的代码,输出为3,但是这个是函数作用域,最后的a 打印的是1

a()
b()
var a=function(){return 1}
function b(){return 2}

a is not a function 2
这里考察的是var 声明的表达式函数和function声明的函数的区别,var声明的变量在提升的时候会赋值为undefined,而函数声明是直接将整个函数提升了

var a='aaa'
function fun(){
console.log(a)
if(false){
let a='bbb'
}
console.log(a)
}
fun()

aaa,aaa

var a='aaa'
function fun(){
console.log(a)
let a='bbb'
console.log(a)
}
fun()

Cannot access ‘a’ before initialization 这个地方是关于let 暂时性死区的问题

let a=2
console.log(window.a)
let b='lucy'
const c=b
b='windy'
console.log(c)
let d={name:'lucy'}
const e=d
d.name='windy'
console.log(e.name)

undefined lucy windy
a在全局定义的变量是不作用于window对象的,const 定义基础变量,一旦定义是不能被更改的,如果是复杂变量是可以改变属性值的

for 循环的作用域

对于let 来说,for(父作用域){子作用域},小括号和花括号的作用域是不同的,对于var 来说是没有区别的,因为var 没块级作用域

for循环的练习题

for(var a=0;a<3;a++){
let a='jjj'
 console.log(a)
}
for (let a=0;a<3;a++){
var a='jjj'
console.log(a)
}
for(let i=0;i<3;i++){
let i='你好'
setTimeout(function(){console.log(i),1000})
}
for(var j=0;j<3;j++){
 var j='bbb'
 console.log(j)
 }

jjj3 Identifier ‘a’ has already been declared 你好3 只有1个 bbb
对于let 父作用域和子作用域是互不影响的,对于var 来说是没有块级作用域的,所以第二个var 会影响 let ,let 在同一作用域下不能同时声明一个变量,所以会报错

for(var a=0;a<3;a++){
  console.log(a)
  setTimeout(function(){
  console.log(a)
  },0)
  }
 for (let a=0;a<3;a++){
 console.log(a)
 setTimeout(function(){
 console.log(a)
 },0)
 }
 

0,1,2 3,3,3
0,1,2,0,1,2
这个涉及到js执行栈,setTimeout 是异步任务,所以会在for 循环执行完毕的时候再执行setTimeout ,var for 循环执行完之后,a 是3 ,所以setTimeout 会执行三个3

function fun(){
for(var a=0;a<5;a++){
console.log(a)
setTimeout(function(){
console.log(a)},0
)
}
for(var a=0;a<3;a++){
console.log(a)
setTimeout(function(){
console.log(a)},0
)
}
}
fun()

0,1,2,3,4
0,1,2
3,3,3,3,3
3,3,3

关于let const var 的分享就到此为止了,有兴趣的小伙伴可以留言谈论哦

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值