ES6 构造函数 returns 基础 class 的实例?
ES6 constructor returns instance of base class?
派生的构造函数classreturns基的实例class。
下面的代码解释了我的问题:
// Vector is defined by an external module (Unreal.js)
class TestB extends Vector {
constructor() {
super();
}
Log() {
console.log("" + this);
}
}
console.log(new TestB() instanceof TestB) // returns false !!! why ???
console.log(new TestB() instanceof Vector) // returns true...
class TestA extends Array {
constructor() {
super();
}
Log() {
console.log("" + this);
}
}
console.log(new TestA() instanceof TestA); // returns true, all is good
这怎么可能?
Vector
的实现方式似乎与 class
不兼容。
这是 Vector
可以做到这一点的一种方式的示例:
function Vector() {
var v = Object.create(Vector.prototype);
return v;
}
class TestB extends Vector {
constructor() {
super();
}
}
console.log(new TestB() instanceof TestB); // false
console.log(new TestB() instanceof Vector); // true
此处的关键在于,由于 Vector
return 与 new
创建的对象不同,因此它的类型错误。关于构造函数的一个相对鲜为人知的事情是,如果它们 return 一个非 null
对象引用, new Constructor
的结果是构造函数 returned 的对象,而不是比 new
创建的对象。
以下是为浏览器支持 class
的用户提供的代码片段:
function Vector() {
var v = Object.create(Vector.prototype);
return v;
}
class TestB extends Vector {
constructor() {
super();
}
}
console.log(new TestB() instanceof TestB); // false
console.log(new TestB() instanceof Vector); // true
...还有一个 live copy on Babel's REPL 给那些浏览器不支持的人。
令我惊讶的是,Babel 和 Chrome 都允许我使用 class Vector
和 returning 来自 constructor
的值;我还没有从规范中弄清楚它是否真的有效:
class Vector {
constructor() {
var v = Object.create(Vector.prototype);
return v;
}
}
class TestB extends Vector {
constructor() {
super();
}
}
console.log(new TestB() instanceof TestB); // false
console.log(new TestB() instanceof Vector); // true
要绕过它,您可能需要使用针对每个实例的 hack,例如将 TestB.prototype
的所有方法复制到实例上。理想情况下,而不是黑客攻击,尝试通过聚合使用 Vector
(又名 "composition",例如,通过将 Vector
实例作为 class 的 属性' s 实例)而不是继承,因为它不是为继承而设置的。
我不知道这个问题的确切原因,但是 hacking proto 解决了这个问题。 :)
class TestB extends Vector {
constructor() {
super();
this.__proto__ = TestB.prototype;
}
Log() {
console.log("" + this);
}
}
派生的构造函数classreturns基的实例class。
下面的代码解释了我的问题:
// Vector is defined by an external module (Unreal.js)
class TestB extends Vector {
constructor() {
super();
}
Log() {
console.log("" + this);
}
}
console.log(new TestB() instanceof TestB) // returns false !!! why ???
console.log(new TestB() instanceof Vector) // returns true...
class TestA extends Array {
constructor() {
super();
}
Log() {
console.log("" + this);
}
}
console.log(new TestA() instanceof TestA); // returns true, all is good
这怎么可能?
Vector
的实现方式似乎与 class
不兼容。
这是 Vector
可以做到这一点的一种方式的示例:
function Vector() {
var v = Object.create(Vector.prototype);
return v;
}
class TestB extends Vector {
constructor() {
super();
}
}
console.log(new TestB() instanceof TestB); // false
console.log(new TestB() instanceof Vector); // true
此处的关键在于,由于 Vector
return 与 new
创建的对象不同,因此它的类型错误。关于构造函数的一个相对鲜为人知的事情是,如果它们 return 一个非 null
对象引用, new Constructor
的结果是构造函数 returned 的对象,而不是比 new
创建的对象。
以下是为浏览器支持 class
的用户提供的代码片段:
function Vector() {
var v = Object.create(Vector.prototype);
return v;
}
class TestB extends Vector {
constructor() {
super();
}
}
console.log(new TestB() instanceof TestB); // false
console.log(new TestB() instanceof Vector); // true
...还有一个 live copy on Babel's REPL 给那些浏览器不支持的人。
令我惊讶的是,Babel 和 Chrome 都允许我使用 class Vector
和 returning 来自 constructor
的值;我还没有从规范中弄清楚它是否真的有效:
class Vector {
constructor() {
var v = Object.create(Vector.prototype);
return v;
}
}
class TestB extends Vector {
constructor() {
super();
}
}
console.log(new TestB() instanceof TestB); // false
console.log(new TestB() instanceof Vector); // true
要绕过它,您可能需要使用针对每个实例的 hack,例如将 TestB.prototype
的所有方法复制到实例上。理想情况下,而不是黑客攻击,尝试通过聚合使用 Vector
(又名 "composition",例如,通过将 Vector
实例作为 class 的 属性' s 实例)而不是继承,因为它不是为继承而设置的。
我不知道这个问题的确切原因,但是 hacking proto 解决了这个问题。 :)
class TestB extends Vector {
constructor() {
super();
this.__proto__ = TestB.prototype;
}
Log() {
console.log("" + this);
}
}