这是我参与11月更文挑战的第8天,活动详情查看:2021最后一次更文挑战。
前言
ECMAScript 6.0 简称ES6 , 是 JavaScript 语言的新一代的标准,于在 2015 年 6 月发布,正式名称就是《ECMAScript 2015 标准》。一般情况,泛指, 5.1版以后的标准,涵盖了 ES2015、ES2016、ES2017、ES2018、ES2019、ES2020、ES2021 等等
今天我们一起来学习变量提升吧。
变量提升是什么
函数声明和变量声明总是被JavaScript解释器隐式地提升(hoist)到包含他们的作用域的最顶端。
function log(){
console.log("name:", name);
var name = "tom";
console.log("name:", name);
}
log();
// name: undefined
// name: tom
其等同于下面的代码:
function log(){
var name;
console.log("name:", name);
name = "tom";
console.log("name:", name);
}
第一个console.log时,其已被申明,但是没有赋值, 第二个console.log的时候,已经赋值。
函数申明 VS 变量申明和赋值
如果普通 变量申明和赋值 遭遇 函数申明,你觉得会怎样呢?
function log(){
console.log("name1:", name);
var name = "tom";
function name(){
console.log("name fun:", nmae);
}
console.log("name2:", name);
}
log();
当然是函数申明胜出,函数表达式其实就是普通的变量申明了。
函数申明 VS 变量申明和赋值 VS 形参
如果再遭遇函数形参呢?
function log(name){
console.log("name1:", name);
var name = "tom";
function name(){
console.log("name fun:", nmae);
}
console.log("name2:", name);
}
log("flower");
结局: 函数申明 > 变量申明 > 形参
不带关键字的变量申明
大家都知道,不带关键的变量申请,会挂载到全局对象上,我们看看其是否能够变量提升。
num1 = 10;
console.log("num1:", num1); // 10
console.log("num1:", num1);
num1 = 10;
// VM521:1 Uncaught ReferenceError: num1 is not defined
可以看到不带var关键的变量申明, 不会变量提升。代码执行到的时候,先查询作用域链,如果未被定义,才会在全局对象上添加对象的属性和值。
let和const不存在变量提升
console.log("num1:", num1);
let num1 = 10;
// Uncaught ReferenceError: num1 is not defined
console.log("num1:", num1);
const num1 = 10;
// Uncaught ReferenceError: num1 is not defined
小测试
var num = 1;
function log() {
if (true) {
var num = 10;
}
console.log(num);
}
log()
console.log(num);
答案输出是 10, 1
var num = 1;
function log() {
if (true) {
num = 10;
}
return;
function num(){}
}
log()
console.log(num);
答案是 1
function arg(){
var arguments;
console.log(arguments);
}
arg(1,2,3);
答案: Arguments(3) [1, 2, 3, callee: ƒ, Symbol(Symbol.iterator): ƒ]
function arg(arguments){
var arguments;
console.log(arguments);
}
arg(1,2,3);
答案: 1
小结
今天你收获了吗?