SOURCE

console 命令行工具 X clear

                    
>
console
// 块级作用域:
// 在没有块级作用域的情况下,内层变量可能覆盖外层变量;
var tmp = Date.now()
function f() {
    if (false) {
        // 这里没有执行,但是由于变量提升的原因,函数 f 的作用域中声明了一个局部变量 tmp
        var tmp = 'hello world'
    }
    // console.log(typeof tmp) // undefined
}
f()

// 在没有块级作用域的情况下,用来计数的循环变量泄漏为全局变量;
var s = 'hello'
for (var i = 0; i < s.length; i++) {
    // console.log(s[i])
}
// console.log(i) 5

// 作用域
function fun1() {
    let n = 5
    if (true) {
        let n = 10;
        // console.log(n) // 10
    }
    // console.log(n) // 5
}
fun1()

// 块级作用域任意嵌套
{
    {
        {
            {
                let instance = 'hello';

            }
            // console.log(instance); // instance is not defined
        }
    }
}

// 块级作用域真正使代码分割成块
{
    let a = 'name'
    // console.log(a) // name
}
{
    let a= 'names'
    // console.log(a) // names
}
// console.log(a) // a is not defined

// 变量提升现象:
// ES5 使用 var 声明变量,出现变量提升的现象。
// console.log(typeof foo); // undefined 
var foo = 2;

// console.log(bar); // cannot access 'bar' before initialzation (初始化之前无法访问)
let bar = 2;

// 不允许重复声明变量
// let、const 不允许在相同块级作用域下声明同一个变量
function func3(arg){
    // let arg // 报错
}
function func4(arg){
    {
        let arg; // 不报错
    }
}

// let、const 声明的全局变量不会挂在到顶层对象下面
let namess = '张三'
// console.log(typeof window.namess) // undefined
const age = 22
// console.log(typeof window.age) // undefined
<h2>var 和 let/const的区别</h2>
<ul>
    <li>块级作用域:<br>没有块级作用域的情况下,内层变量可能覆盖外层变量;<br>用来计数的循环变量泄漏为全局变量;<br>ES6的块级作用域允许声明函数的规则,只在使用大括号的情况下成立,如果没有使用大括号,就会报错。</li>
    <li>不存在变量提升:<br>在同一作用域下,变量可以在声明之前使用,值为 undefined;<br />ES5 时使用 var 声明变量,经常会出现变量提升的现象。</li>
    <li>暂时性死区:<br>只要进入当前作用域,所要使用的变量就已经存在了,但是不可获取,只有等到声明变量的那一行代码出现,才可以获取和使用该变量。<br>暂时性死区可以减少运行时的错误,防止在变量声明前就使用这个变量</li>
    <li>不可重复声明:<br>let、const不允许在相同作用域内,重复声明同一个变量。</li>
    <li>let、const 声明的全局变量不会挂在顶层对象下面:<br />1. 浏览器环境顶层对象是:window<br />2. node 环境顶层对象是:global<br>var 声明的全局变量会挂在顶层对象下面,而 let、const不会挂在顶层对象下面</li>
</ul>
<h3>const 命令两个注意点:</h3>
<ul>
    <li>const 声明之后必须马上赋值,否则会报错</li>
    <li>const 简单类型一旦声明就不能更改,引用类型指针指向的地址不能更改,内部数据可以更改</li>
</ul>
<h3>let、const使用场景</h3>
<ul>
    <li>let 使用场景:变量,用以替代 var</li>
    <li>const 使用场景:常量,声明匿名函数、箭头函数的时候</li>
</ul>