调用基类构造函数而不手动提供参数

时间:2016-12-01 12:11:35

标签: javascript class constructor ecmascript-6

想象一下,我们有以下class

class A {
       constructor(x, y, z) {
       }
}

class B extends A {
     constructor(x, y, z) {
         super(x, y, z);
     }
}

如果我们想使用super(...)其他参数致电arguments该怎么办:

super.apply(this, arguments);
super.apply(this, args);

这不起作用:super.* 之前不允许 super()

有没有其他方法可以避免手动提供参数?

2 个答案:

答案 0 :(得分:3)

class A {
       constructor(x, y, z) {
         console.log(x,y,z);
       }
}

class B extends A {
     constructor(x, y, z) {
         super(...arguments);
     }
}

let X = new B(1,2,3);

答案 1 :(得分:2)

使用点差表示法:

super(...args);

E.g:

class B extends A {
    constructor(...args) {
        super(...args);
    }
}

super(...arguments)也可以。)

但值得注意的是,对于显示的AB,您无需为B 提供构造函数。派生类的默认构造函数¹如上所示,所以:

class B extends A {
}

会做同样的事情。

以下进一步举例。

在评论中,你说基类有10个(!)参数,你的子类只需要其中两个,我的印象是你的意思是第一个两个。如果是这样的话:

class B extends A {
    constructor(first, second, ...rest) {
        super(first, second, ...rest);
        // Use `first` and `second` here...
    }
}

如果你的意思是中间的两个,我们也可以通过解构来做到这一点:

class B extends A {
    constructor(...args) {
        super(...args);
        let {1: second, 2: third} = args;
        // Use `second` and `third` here...
    }
}

更多例子:

class A {
  constructor(x, y, z) {
    console.log(`A: ${x}, ${y}, ${z}`);
  }
}

// No constructor defined; gets default
class B1 extends A {}

// Explicit version of the default constructor
class B2 extends A {
  constructor(...args) {
    super(...args);
  }
}

// Using `arguments` instead:
class B3 extends A {
  constructor() {
    super(...arguments);
  }
}

// If the subclass accepts different args
class B4 extends A {
  constructor(q, ...rest) {
    super(...rest);
    console.log(`B4: q = ${q}`);
  }
}

class B5 extends A {
  constructor(...args) {
    super(...args);
    // They don't have to be called `y` and `z`, I'm just being consistent
    let { 1: y, 2: z } = args;
    console.log(`B5: y = ${y}, z = ${z}`);
  }
}

new B1(1, 2, 3);
new B2(4, 5, 6);
new B3(7, 8, 9);
new B4('q', 'x', 'y', 'z');
new B5('first', 'second', 'third');

¹“子类的默认构造函数完全如上所示”注意这与Java或C#等语言有何不同,默认构造函数不接受args并调用{{1} } / super()没有args。