如何在非ES6 Javascript中处理类扩展?

时间:2018-01-04 17:00:29

标签: javascript ecmascript-6

对于Javascript的基于原型的继承系统,ES6 class关键字仅为said syntactic sugar。这一点很明显,只有一个例外:extends关键字。例如:

class Foo {
    constructor(){
        this.sayHello = () => console.log('Hello')
    }
}

class Bar extends Foo {
    constructor(){
        super(); 
        this.sayGoodbye = () => console.log('Goodbye');
    }
}

如果class只是语法糖,那么这里发生了什么?是否有标准< ES6设计模式,模拟被调用的类继承,或者这是一些新功能?

2 个答案:

答案 0 :(得分:1)

  

是否有标准< ES6设计模式,模拟被调用的类继承?

JavaScript有一个原型继承模型,这也是class关键字的结果。您的代码大致相当于:

function Foo () {
    this.sayHello = () => console.log('Hello')
}

function Bar () {
    // super();
    Foo.call( this );

    this.sayGoodbye = () => console.log('Goodbye');
}

// extends
Bar.prototype = Object.create( Foo.prototype );
Bar.prototype.constructor = Bar;

答案 1 :(得分:-1)

  

引擎盖下发生了什么?

这是JS引擎的实现细节。

  

是否有标准< ES6设计模式,模拟正在调用的类继承

"标准"可能走得太远,但Babel是一个众所周知的转换器,可以将ES6转换为ES5。

它给出了这个:

'use strict';

function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }

function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }

function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }

var Foo = function Foo() {
    _classCallCheck(this, Foo);

    this.sayHello = function () {
        return console.log('Hello');
    };
};

var Bar = function (_Foo) {
    _inherits(Bar, _Foo);

    function Bar() {
        _classCallCheck(this, Bar);

        var _this = _possibleConstructorReturn(this, (Bar.__proto__ || Object.getPrototypeOf(Bar)).call(this));

        _this.sayGoodbye = function () {
            return console.log('Goodbye');
        };
        return _this;
    }

    return Bar;
}(Foo);