let和const命令

1.let命令

基本用法:

    let命令用来声明变量,只在let命令所在的代码块中有效
   
   
  1. for(let i = 0; i < 10; i++) {}
  2. console.log(i);//not defined
    以上代码i只在for循环中有效。
    与var声明变量作比较:
   
   
  1. var a = [];
  2. for (var i = 0; i < 10; i++) {
  3. a[i] = function () {
  4. console.log(i);
  5. };
  6. }
  7. a[6](); // 10
    i通过var声明,在全局范围内有效,数组a的function通过闭包读到i,最后输出的是最后一轮i的值。
   
   
  1. var a = [];
  2. for (let i = 0; i < 10; i++) {
  3. a[i] = function () {
  4. console.log(i);
  5. };
  6. }
  7. a[6](); // 6
    当前i只在本轮循环有效,每次循环的i是一个新的变量,设置循环的部分是一个父作用域,循环体内是一个单独的子作用域。

不存在变量提升:

    var声明变量可以在声明之前使用变量,值为undefined;
    let命令声明变量一定要在声明后使用,否则会报错,变量不可用,这称为   “暂时性死区”(temporal dead zone,简称 TDZ), 在let声明bar变量之前,都属于bar的死区。
   
   
  1. // var 的情况
  2. console.log(foo); // 输出undefined
  3. var foo = 2;
  4. // let 的情况
  5. console.log(bar); // 报错ReferenceError
  6. let bar = 2;

 不允许重复声明:

    let不允许在相同作用域内,重复声明同一个变量。
   
   
  1. function func(arg) {
  2. let arg; // 报错
  3. }
  4. function func(arg) {
  5. {
  6. let arg; // 不报错
  7. }
  8. }

2.块级作用域

    let为javascript新增了块级作用域,“同层”的代码作用域相同。
   
   
  1. function f1() {
  2. let n = 5;
  3. if (true) {
  4. let n = 10;
  5. }
  6. console.log(n); // 5
  7. }

块级作用域和函数声明

    ES5中不允许在块级作用域声明函数,函数只能在顶层作用域和函数作用域中声明。
   
   
  1. //非法情况
  2. // 情况一
  3. if (true) {
  4. function f() {}
  5. }
  6. // 情况二
  7. try {
  8. function f() {}
  9. } catch(e) {
  10. // ...
  11. }
    ES6允许在块级作用域之中声明函数,函数声明语句的行为类似于let,在块级作用域之外不可引用。
    作用域对比:
   
   
  1. function f() { console.log('I am outside!'); }
  2. (function () {
  3. if (false) {
  4. // 重复声明一次函数f
  5. function f() { console.log('I am inside!'); }
  6. }
  7. f();
  8. }());
    在ES5中,if内声明的f函数会提升到函数的头部,即:
   
   
  1. // ES5 环境
  2. function f() { console.log('I am outside!'); }
  3. (function () {
  4. function f() { console.log('I am inside!'); }
  5. if (false) {
  6. }
  7. f();
  8. }());
    在ES6中,函数声明类似于var,提升到全局作用域或函数作用域的头部,即:
   
   
  1. // 浏览器的 ES6 环境
  2. function f() { console.log('I am outside!'); }
  3. (function () {
  4. //相当于在这里声明了var f = undefined;
  5. if (false) {
  6. // 重复声明一次函数f
  7. function f() { console.log('I am inside!'); }
  8. }
  9. f();
  10. }());
  11. // Uncaught TypeError: f is not a function
    解决办法:避免在块级作用域内声明函数,应该写成函数表达式。
   
   
  1. // 函数声明语句
  2. {
  3. let a = 'secret';
  4. function f() {
  5. return a;
  6. }
  7. }
  8. // 函数表达式
  9. {
  10. let a = 'secret';
  11. let f = function () {
  12. return a;
  13. };
  14. }

do表达式

    do表达式,用于返回块级作用域的值:
   
   
  1. let x = do {
  2. let t = f();
  3. t * t + 1;
  4. };
    变量x会得到整个块级作用域的返回值。

3.const命令

    const声明一个只读的常量,一旦声明,值不能改变,必须立刻初始化,只声明不赋值会报错,只在声明所在的块级作用域内有效,与let相同,常量也不提升,存在暂时性死区,只能在声明的位置后面使用,不可重复声明。
    const事实上保证指向的内存地址不得改动,对于简单数据类型(数值、字符串、布尔值),值就保存在变量指向的那个内存地址,等同于常量。复合类型(对象和数组),变量指向的内存地址, 保存的只是一个指针,const只能保证指针是固定的。

4.顶层对象的属性

    ES5中,顶层对象(window)的属性的赋值等同于全局变量的赋值,不利于模块化编程。
    ES6改变了这一段,保留了var命令和function命令声明的全局变量,依旧是顶层对象的属性,但是let命令、const命令、class命令声明的全局变量,不属于顶层对象的属性。
   
   
  1. var a = 1;
  2. // 如果在Node的REPL环境,可以写成global.a
  3. // 或者采用通用方法,写成this.a
  4. window.a // 1
  5. let b = 1;
  6. window.b // undefined

5.global对象

    在system.global中,global作为全局变量,在所有的环境(浏览器环境、node环境、web worker环境)中都能从它拿到顶层对象。
   
   
  1. // CommonJS的写法
  2. require('system.global/shim')();
  3. var global = require('system.global')();
  4. // ES6模块的写法
  5. import shim from 'system.global/shim'; shim();
  6. import getGlobal from 'system.global'; const global = getGlobal();
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值