• ES6之class


    ES6之class

      es6中的class是一个基于prototype继承的语法糖,它提供了更接近传统语言的写法,引入了class(类)这个概念作为对象的模版。通过class关键字可以定义类,但是通过class做的工作,es5也可以做到,只是通过class,可以使我们的工作更加方便。

      

    第一部分:class定义

      class实际上是一种特殊的函数,就像我们可以通过函数表达式和函数声明来定义函数一样,class也有这两种定义方式。

      1.class声明

      只需使用class关键字,并在其后加上class名称即可,如:

    class Polygon{

      constructor(width,height){

        this.width=width;

        this.height=height;

      }

    }

       

       注意:普通的函数声明的特点在于:函数声明提升。但是class的函数声明没有函数声明提升,这一点要格外注意。

      

      2.class表达式

       class表达式可以是匿名的,也可以不是。

      不匿名:

      

    var Polygon = class Polygon{

      constructor(width,height){

        this.width=width;

        this.height=height;

      }

    };

       

      匿名:

      

    var Polygon = class{

      constructor(width,height){

        this.width=width;

        this.height=height;

      }

    }; 

      同样的,函数表达式也没有提升的效果

    第二部分:class主体和方法

      class的主体部分使用{}括起来的,我们可以在其中定义class成员。比如方法和constructor。且他们都是在严格模式下运行的。

      constructor是为了创建和初始化一个有class产生的对象的,在class中只能有一个class方法, 并且在construtor中可以使用super关键字调用父类的constructor

      原型方法:

    class Polygon {
      constructor(height, width) {
        this.height = height;
        this.width = width;
      }
      
      get area() {
        return this.calcArea();
      }
    
      calcArea() {
        return this.height * this.width;
      }
    }
    
    const square = new Polygon(10, 10);
    
    console.log(square.area);

      我们可以看到,在这个类中不仅有constructor方法,还有其他两个方法。

      值得注意的是:在定义“类”方法时,前面不需要加function关键字,直接把函数定义进去就可以了,且方法之间不需要加逗号分隔,否则会报错。

       

      重点:

      ES6中的类完全可以看作构造函数的另一种写法:

     class Polygon {

      //...  

    }

      typeof Point //“function”

      Point === Point.prototype.constructor // true

       也就是说,对于下面的这个类:

    class Polygon {
      constructor(){

         // ...

          }

         toString(){

      //...

      }

      toValue(){

      //...

      }

    }

       使用es5来写可以写成这样:

      Polygon.prototype = {

        constructor(){},

        toString(){},

        toValue(){}

      }

       

      也就是就说,在类的实例上调用方法,实际上就是调用原型上的方法。

      class B {}

      let b = new B{};

      b.constructor === B.prototype.constructor //true

       即b是B类的实例,它的constructor方法就是B类原型的constructor方法。

      

      

     第三部分:实例对象

      生成实例对象的方法和ES5完全相同,使用new命令即可。如:

      var polygon = new Polygon();

       

      值得注意的是:实例的属性除非显示定义在其本身(即this对象)上,否则都是定义在原型上的。

      与ES5一样,类的所有实例共享一个原型对象。如下所示:  

      var polygon1 = new Polygon();

      var polygon2 = new Polygon();

      polygon1._proto_ === polygon2._proto_   //true

      在上面的代码中,p1和p2都是Polygon的实例,他们的原型都是Point,所以_proto_属性时相等的。这也意味着,我们可以通过实例的_proto_属性为class添加方法。

      polygon1._proto_.getArea = function () {return 100};

      polygon2.getArea(); //100

       

       下面是一个简单的例子:

    class Polygon {
      constructor(height, width) {
        this.height = height;
        this.width = width;
      }
      
      get area() {
        return this.calcArea();
      }
    
      calcArea() {
        return this.height * this.width;
      }
    }
    
    const square = new Polygon(20, 20);
    const sss = new Polygon(10,250);
    console.log(square._proto_ === sss._proto_); //true
    console.log(square.area); //400
    console.log(sss.area); //2500

    第四部分:继承

      class之间可以通过extends实现继承,这比ES5通过修改原型链实现继承要清晰和方便很多。如:

    class ColorPolygon extends Polygon {}

      上面的代码定义了一个ColorPolygon类,该类通过extends关键字继承了Polygon类中的所有属性和方法,但是上面的这行代码由于我们没有部署任何代码,所以这两个类目前是完全一样的,等于复制了一个Polygon类。

      如果我们给这个ColorPolygon类进行部署:

    class ColorPolygon extends Polygon {

      constructor(width,height,color){

        super(width,height); //通过super关键字来调用父类的constructor(width,height)

        this.color = color;

      }

      toString(){

        return this.color + ' ' + super.someFunc(); // 如果父类中有一个方法someFunc,我们就可以通过关键字super来调用父类的toString()

      }

      

      于是我们可以看到,constructor方法和toString方法中都出现了super关键字,它指代父类的实例(即父类的this对象),且子类必须在constructor方法中调用super方法,否则新建实例时会报错,这是因为子类中没有自己的this对象,而是继承了父类的this对象,然后对其进行加工。如果不调用super方法,子类就得不到this对象。

      

  • 相关阅读:
    程序员学习参考网站
    博客
    window对象
    事件触发顺序
    element对象
    正则表达式
    Date对象
    Number对象
    Math对象
    Binary Tree Maximum Path Sum
  • 原文地址:https://www.cnblogs.com/zhuzhenwei918/p/6362597.html
Copyright © 2020-2023  润新知