• ECMAScript 6


    1.  ECMAScript 6 简介

    官网:http://es6.ruanyifeng.com/

    ECMAScript 6.0(简称 ES6)是 JavaScript 语言的下一代标准,于 2015 年 6 月正式发布。

    • ECMAScript 和 JavaScript 是什么关系?

      1996 年 11 月,JavaScript 的创造者 Netscape 公司,希望JavaScript能够成为国际标准,将其提交给标准化组织 ECMA。次年,ECMA 发布了ECMAScript 1.0 版。不叫 JavaScript的原因:一是商标,JavaScript 已被 Netscape 公司注册为商标;二是体现其制定者是 ECMA,不是 Netscape,有利于保证其的开放性和中立性。

      前者是后者的规格,后者是前者的一种实现(另外的 ECMAScript 方言还有 Jscript 和 ActionScript)。

    语法提案的批准流程

    任何人都可以向标准委员会(又称 TC39 委员会)提案,要求修改语言标准。

    一种新的语法从提案到变成正式标准,需要经历五个阶段。每个阶段的变动都需要由 TC39 委员会批准。

    • Stage 0 - Strawman(展示阶段)
    • Stage 1 - Proposal(征求意见阶段)
    • Stage 2 - Draft(草案阶段)
    • Stage 3 - Candidate(候选人阶段)
    • Stage 4 - Finished(定案阶段)

    一个提案只要能进入 Stage 2,就差不多肯定会包括在以后的正式标准里面。ECMAScript 当前的所有提案,可以在 TC39 的官方网站Github.com/tc39/ecma262查看。

    ECMAJavaScript 历史:

    1998年6月,ECMAScript 2.0版发布。

    1999年12月,ECMAScript 3.0版发布,成为JavaScript的通行标准。

    2007年10月,ECMAScript 4.0版草案发布,对3.0版做了大幅升级,预计次年8月发布正式版本。草案发布后,由于4.0版的目标过于激进,各方对于是否通过这个标准,发生了严重分歧。以Yahoo、Microsoft、Google为首的大公司,反对JavaScript的大幅升级,主张小幅改动;以JavaScript创造者Brendan Eich为首的Mozilla公司,则坚持当前的草案。

    2008年7月,由于对于下一个版本应该包括哪些功能,各方分歧太大,争论过于激进,ECMA开会决定,中止ECMAScript 4.0的开发,将其中涉及现有功能改善的一小部分,发布为ECMAScript 3.1,而将其他激进的设想扩大范围,放入以后的版本,由于会议的气氛,该版本的项目代号起名为Harmony(和谐)。会后不久,ECMAScript 3.1就改名为ECMAScript 5。

    2009年12月,ECMAScript 5.0版正式发布。Harmony项目则一分为二,一些较为可行的设想定名为JavaScript.next继续开发,后来演变成ECMAScript 6;一些不是很成熟的设想,则被视为JavaScript.next.next,在更远的将来再考虑推出。

    2011年6月,ECMAscript 5.1版发布,并且成为ISO国际标准(ISO/IEC 16262:2011)。

    2013年3月,ECMAScript 6草案冻结,不再添加新功能。新的功能设想将被放到ECMAScript 7。

    2013年12月,ECMAScript 6草案发布。然后是12个月的讨论期,听取各方反馈。

    2015年6月17日,ECMAScript 6发布正式版本,即ECMAScript 2015

    ECMA的第39号技术专家委员会(Technical Committee 39,简称TC39)负责制订ECMAScript标准,成员包括Microsoft、Mozilla、Google等大公司。TC39的总体考虑是,ES5与ES3基本保持兼容,较大的语法修正和新功能加入,将由JavaScript.next完成。

    2. let 和 const 命令

    先回顾一下JavaScript 中的声明变量  var 

    • 函数作用域
    function sum(){
        var a=10;
    }
    console.log(a);//结果会报错

    • 可重复声明
    var a=10;
    var a=20;
    console.log(a);//结果为20

    • 有变量提升的现象
    console.log(a);//结果为undefined,声明提前,赋值不提前
    var a = 10;

    • 可先声明后赋值
    var a;
    a = 10;
    console.log(a);//结果为10

    • let声明变量

      •   块状作用域(任意大括号包含的变量都只在大括号里起作用,超出则报错)
    {let a=20;}
    console.log(a);//报错

    例子:

    //使用var
    var a = []; for (var i = 0; i < 5; i++) { a[i] = function () { console.log(i); }; } a[3](); // 结果为5
    //使用let
    var a = []; for (let i = 0; i < 5; i++) { a[i] = function () { console.log(i); }; } a[3](); // 结果为3
      •   不能重复声明
    let a=20;
    let a=10;
    console.log(a);//报错

      •   没有变量提升
    console.log(a);//报错
    let a=20;

      •   暂时性死区(在代码块内,使用let命令声明变量之前,该变量都是不可用的),简称TDZ
    var a = 123;
    if (true) {
        a = 'abc'; 
        let a;//在let命令声明变量a之前,都属于变量a的“死区”。
    }

    注:使用let声明变量时,只要变量在还没有声明完成前使用,就会报错。

    let x=x;//在变量x的声明语句还未执行完成前去取x的值,导致报错”x 未定义“。
    • const 声明常量(声明一个只读的常量。一旦声明,常量值不可变)
      •   声明必须同时赋值
    const a;
    a=20;
    console.log(a);//报错

      •   const 声明与 let 声明一样:无变量提升、块级作用域、暂时性死区、不可重复声明。

    3. 变量的解构赋值

    • 数组的解构赋值:按照一定模式,从数组和对象中提取值,对变量进行赋值
    let [a, b, c] = [1, 2, 3];//相当于let a = 1;let b = 2;let c = 3;
      •   模式匹配(等号两边的模式相同,左边的变量将被赋予对应的值)。若解构不成功,变量的值为 undefined
    let [a, [[b], c]] = [1, [[2], 3]];//a = 1,b = 2,c = 3
    let [x, , y] = [1, 2, 3];//x = 1,y = 3
    let [head, ...tail] = [1, 2, 3, 4];//head = 1,tail = [2, 3, 4]
    let [x, y, ...z] = ['a'];//x = "a",y:undefined,z:[]
    let [x, y] = [1, 2, 3];//x = 1, y = 2
    let [a, [b], d] = [1, [2, 3], 4];//a = 1,b = 2,d = 4

    注:若等号右边非数组,即不可遍历的结构,将会报错。

    let [a] = 1;//报错
      •   Set 结构可用数组的解构赋值
    let [x, y, z] = new Set(['a', 'b', 'c']);
      •   解构赋值允许指定默认值
    let [x, y = 'b'] = ['a']; // 或let [x, y = 'b'] = ['a', undefined]; x='a', y='b'

    注:ES6 用严格相等运算符(===),判断一个位置是否有值。只有当一个数组成员严格等于undefined,默认值才会生效。(null不严格等于undefined

    let [x = 1] = [undefined];//x = 1
    let [x = 1] = [null];//x:null
      •   若默认值是一个表达式,该表达式是惰性求值的,即只在用到时才会求值。
      •   默认值可引用解构赋值的其他变量(该变量必已声明)。
    let [x = 1, y = x] = [];     // x=1; y=1
    let [x = 1, y = x] = [2];    // x=2; y=2
    let [x = 1, y = x] = [1, 2]; // x=1; y=2
    let [x = y, y = 1] = [];     //报错,x用y做默认值时,y还未声明。
      •   用于交换数据
    var a = 10,b = 20;
    var [a, b] = [b, a];
    console.log(a, b);  //a = 20,b = 10
    • 字符串的解构赋值
    let [a, b] = 'hi'; // a='h',a='i'
    • 对象的解构赋值
      •   对象的属性无次序,变量必与属性同名,才取到正确的值。若解构失败,变量的值等于undefined
    let { a, b } = { a: "aa", b: "bb" }; // a="aa",b="bb"
    let { c } = { a: "aa"};//c: undefined
      •   若变量名与属性名不同,写法如下:
    let { a: c } = { a: 'aa'}; //c = "aa"

    注:对象的解构赋值是先找到同名属性,再赋给对应的变量。真正被赋值的是后者,而非前者。

      •   对象的解构也可指定默认值
    var {x:y = 3} = {}; //y= 3

    注:默认值生效的条件:对象的属性值严格等于undefined

    4. 字符串的扩展

    • 模板字符串
    var y = 2018,m = 5,d = 7;
    var str = `今天是${y}年${m}月${d}日`;
    • 部分新方法
    var str = "hello";
    //判断是否包含某指定的字符
    var res1 = str.includes("d");//res1结果为 false
    //判断是否以某字符开头
    var res2 = str.startsWith("e");//res2结果为 false
    //判断是否一某字符结尾 var res3 = str.endsWith("o");//res3结果为 true //让字符串重复几次 var res4 = str.repeat(3);//res4结果为 hellohellohello

    5. 函数的扩展

    • 默认值
    //函数的默认值
    function fn(a,b = 20) {
        console.log(a,b);
    }
    fn(10);//结果为10 20
    • 剩余参数
    //剩余参数
    function fn(a,...b) {
        console.log(a,b);
    }
    fn(10,[2,3,4]);//结果为 
    • 箭头函数
    //有参数
    var fn1=num=>num;//相当于var fn1=function(num){return num;}
    //无参数
    var fn2=()=>10;//相当于var fn2=function(){return 10;}
    //多个参数
    var fn3=(num1,num2)=>num1+mun2;//或者var fn3=(num1,num2)=>{return num1+num2};
    //map的用法
    [1,2,3].map(num=>num*2);//相当于var fn=[1,2,3].map(function(num){return num*2;});

    6. set方法

    Set是一个构造函数,可创建出类似于数组的数据结构一般用于创建不重复的数组

    //创建set数组
    var arr=new Set([1,2,3]);
    //添加数据
    arr.add(4);
    //删除指定数据
    arr.delete(4);//判断数组是否有某指定元素
    var res=arr.has(2);//res 结果为 true
    //控制台输出数组元素 for(let [key,value] of arr.entries()){ console.log(value); }
    //删除所有元素
    arr.clear();

    7. promise 的用法

    • 回调函数
    function a(callBack) {
        console.log("我是主函数");
        callBack();
    }
    function b() {
        console.log("我是回调函数")
    }
    a(b);
    • 多层回调
    function run() {
      var obj=new Promise(function (resolve,reject) {
        resolve("运行成功的函数");
        reject("运行失败的函数");
      })
      return obj;
    }
    run().then(function () {
      //执行一些功能
    }).then(function () {
      //再执行一些功能
    })

    8. 类与继承

    class Person{
      constructor(name,age){
        this.name=name;
        this.age=age;
      }
      static tell(){
        alert("hello");
      }
      say(){
        alert(this.name+this.age);
      }
    }
    var per=new Person("David",23);
    console.log(per.name);
    per.say();
    //static修饰的方法是类直接调用的不能用new出来的对象调用Person.tell();
    class Student extends Person{
      constructor(name,age,score){
        super(name,age);
        this.score = score;
      }
      show(){
        alert(this.name + this.score);
      }
    }
    var stu=new Student("Nancy",24,80);
    stu.show();
    stu.say();

    注:static修饰的方法是类直接调用的不能用new出来的对象调用

     (未完,详细晚点更新)

  • 相关阅读:
    借用构造函数实现继承
    原型链
    创建对象 之 组合使用构造函数模式和原型模式
    6.原型对象的问题
    Spring MVC
    AOP
    谈谈对Spring IOC的理解
    Mybatis3.x与Spring4.x整合(转)
    手把手Maven搭建SpringMVC+Spring+MyBatis框架(超级详细版)
    Appweb写法
  • 原文地址:https://www.cnblogs.com/writerW/p/8994633.html
Copyright © 2020-2023  润新知