var关键字

var可以声明一个变量,当未赋值时其值未undefined,var声明的变量不仅可以重新赋值,还可以改变指的类型,例如:

var message='hi'
    message=100

上面的例子对var声明的变量,不仅重新赋值也改变了变量的类型。

1. var声明作用域

var声明的变量也分为全局变量和局部变量:
全局变量:在js文件函数体外定义的变量为全局变量,在函数体中也可以使用。
局部变量:在函数中定义的var 变量为局部变量,该变量只在函数中奏效,随着函数体}结束而销毁。
注意:在函数体中直接用 a=10,的方式定义的变量为全局变量,一般不建议这种方式定义。
例如:

function test(){
  message=10
}
console.log(message) //输出为10,变为了全局变量

拓展:声明多个变量还可以使用var a='xxx',b=10,c=true;

2. var声明提升
使用var声明的变量,下面代码不会报错,这是因为是用这个关键字提升的变量会自动提升到函数作用域顶部:

function foo(){
console.log(message)
var message=10
}
foo() //输出为undefined

上面的代码不会报错即因为变量提升的缘故,但是变量提升并不会对值的提升所以上面的例子输入为undefined,即等价于:

function foo(){
var message;
conole.log(message)
message=10
}
foo()

另外反复多次声明一个变量也没有问题,例如:

function foo(){
var age=10
var age=20
var age=30
}

上述例子并不会报错即因为var可以反复多次声明一个变量,后面的const却不可以。

let声明

let跟var作用差不多,但最大的区别时var声明的变量作用域是函数作用域,而let是块作用域,例如:

//var声明
if(true){
var name='xxx'
console.log(name) //输出:xxx
}
console.log(name) //输出:xxx
//let声明
if(true){
let age=26
console.log(age) //输出:26
}
console.log(age) //报错

let不允许同一个块作用域中出现冗余声明,这点即和var不一样。

//var冗余声明不会报错
var name;
var name;
//let冗余声明会报错
let age;
let age;

拓展

  • 嵌套声明的let变量不会报错,如下:
let age=20
console.log(age)
if(true){
let age=26
console.log(age)
}

上述例子let重复声明并不会报错是因为let声明的变量不在一个块级作用域内

  • 声明的变量并不会因为var let混用而不出现冗余报错:
let age=22
var age=33
var name='w'
let name='e'

上述的声明依然会出现冗余报错

let的其他特性

1. let声明的变量在作用域中不会被提升

console.log(age) //报错
let age=10

2. let全局声明的变量并不会成为window对象的属性,而var声明的变量会成为window对象的属性

var name=10
console.log(window.name)//输出为10
let name=10
console.log(window.name) //undefined

3. for循环中的let声明

  • let的for循环变量不会渗透到循环体外面,而for循环的变量会渗透到循环体的外面:
for(var i=0;i<5;i++){

}
console.log(i) //输出5

for(let i=0;i<5;i++){

}
console.log(i) //报错
  • for循环中let和var迭代变量的声明和修改:

let的迭代声明:

for(let i=0;i<5;i++){
setTimeout(()=>{console.log(i)},0)
}
//输出 0,1,2,3,4

上述例子中会为每个迭代循环声明一个新的迭代变量,每个setTimeout引用的都是不同的迭代变量。

var的迭代声明:

for(var i=0;i<5;i++){
setTimeout(()=>{console.log(i)},0)
}
//输出:5,5,5,5,5

上述例子中迭代变量保存的是导致退出循环的i值,所以输出:5,5,5,5,5。

const声明

const与let基本相同,区别在于声明变量的同时必须初始化,且const初始化好的变量不可修改。

const age=16
age=18 //会报错,给常量赋值

const不允许重复赋值

const age=18
const age=12 //报错

const声明的作用域也是块

const name=16
if(true){
const name=18
}
console.log(name) //输出16

const声明的限制只适用于它指向的变量的引用,即const引用的是一个对象,修改对象内部的属性不会报错。

const person={}
person.name='david'

const在for循环中不可作为迭代变量,因为修改了其值,但是在for-of,for-in中可以使用,每次迭代相当于创建了一个新的变量。

for(const i=0;i<10;i++){} //报错

for(const key in {a:1,b:2}){
console.log(key)
}
//输出:a b
 
for(const value of [1,2,3]){
console.log(value)
}
//输出:1,2,3
最后修改:2021 年 10 月 22 日
如果觉得我的文章对你有用,请随意赞赏