javascript __proto__ 不会产生与 "prototype"继承相同的效果

标签 javascript inheritance prototype proto

这次使用“proto”的主要原因是试图将继承定义保留在函数定义中:

设置函数 def 外的继承,仅适用于只能通过“this.xxx”访问“公共(public)字段”的函数,并且 Inheriting_FuncDef 必须具有 SuperFuncDef 的扩展知识,否则“公共(public)字段”将发生碰撞:

var G=function (){
    var g1state=0;
    this.g1=function(){
        return g1state++;
    }
};
var E = function (){

    var e2state=0;
    this.e2=function(){
        return e2state++;
    }
};
E.prototype=new G();

var F= function (){

    var f3state=0;
    this.f3=function(){
        return f3state++;
    }
};
F.prototype=new E();


var xx = new F();
var xx2= new F();

console.log("xxg1:___"+xx.g1());//0
console.log("xxg1:___"+xx.g1());//1
console.log("xx2g1:___"+xx2.g1());//2 , need it to be 0, don't wanna share same super() instance/and closure.


console.log("xxe2:___"+xx.e2());//0
console.log("xxe2:___"+xx.e2());//1
console.log("xx2e2:___"+xx2.e2());//2 , need it to be 0;don't wanna share same super() instance/and closure.


console.log("xxf3:___"+xx.f3());//0
console.log("xxf3:___"+xx.f3());//1
console.log("xx2f3:___"+xx2.f3());//0 this f3() is not inherited from super(), and have the expected result. 

console.log(xx);
console.log("xx instanceof E:___"+(xx instanceof E));//ture
console.log("xx instanceof F:___"+(xx instanceof F));//true
console.log("xx instanceof G:___"+(xx instanceof G));//ture

对于“改进版”,似乎唯一的缺点是:“instancof”测试不能正确,否则可用。但“instancof”的错误是一个主要缺点。

//i test it in ie 11, the result is the same.
var G=function (){
    var g1state=0;
    this.g1=function(){
        return g1state++;
    }
};
var E = function (){
    Object.setPrototypeOf(this,new G());
    var e2state=0;
    this.e2=function(){
        return e2state++;
    }
};
//E.prototype=new G();
var F= function (){
    Object.setPrototypeOf(this,new E());
    var f3state=0;
    this.f3=function(){
        return f3state++;
    }
};
//F.prototype=new E();

var xx = new F();
var xx2= new F();

console.log("xxg1:___"+xx.g1());//xxg1:___0  ,expected.
console.log("xxg1:___"+xx.g1());//xxg1:___1  ,expected.
console.log("xx2g1:___"+xx2.g1());//xx2g1:___0  ,expected.


console.log("xxe2:___"+xx.e2());//xxe2:___0  ,expected.
console.log("xxe2:___"+xx.e2());//xxe2:___1  ,expected.
console.log("xx2e2:___"+xx2.e2());//xx2e2:___0  ,expected.


console.log("xxf3:___"+xx.f3());//xxf3:___0  ,expected.
console.log("xxf3:___"+xx.f3());//xxf3:___1  ,expected.
console.log("xx2f3:___"+xx2.f3());//xx2f3:___0  ,expected.


console.log(xx);
console.log("xx instanceof E:___"+(xx instanceof E));//xx instanceof E:___false , expect to be true
console.log("xx instanceof F:___"+(xx instanceof F));//xx instanceof F:___false, expect to be true
console.log("xx instanceof G:___"+(xx instanceof G));//xx instanceof G:___true

所以无论哪种方式都无法产生完美的结果。我认为继承设置的“Funcref.prototype=new superFuncref()”方式对我来说基本上不起作用。

也是我这样做的唯一原因 Object.setPrototypeOf(this,new SuperFuncRef());是因为我希望所有“instancof”子句都为真,否则,我会执行 SuperFuncRef().apply(this),首先将所有函数复制到“this”中,然后进行本地覆盖。因此 new F() 只是 F 的一个实例,这不是我想要的。

感谢您的关注。如果你不在乎,或者认为不值得,请不要管它,不要浪费更多时间来给它投反对票,我处于边缘,或者你可以通过在下面评论来教我英语语法。我会一次又一次地重新格式化,直到你满意为止,不管你是否给出答案。

最佳答案

为什么您要尝试在构造函数中执行所有操作?这是低效的,没有任何意义。你也不应该触摸 __proto__ 除非你有一些罕见的需要这样做。

这是一种设置继承的正统方法(并且在执行期间没有每个成员函数的单独副本)。注意使用 Object.create() 而不是 new:

//test in chrome_v36 only
var G = function() {
};
G.prototype.g1 = function() {};

var E = function() {
};
E.prototype = Object.create(G.prototype); 
E.prototype.e2 = function() {};

var F = function() {
};
F.prototype = Object.create(E.prototype); 
F.prototype.f3 = function() {};

var xx = new F();
console.log(xx); //F {f3: function, e2: function, g1: function}
console.log("xx instanceof E:___" + (xx instanceof E)); // true
console.log("xx instanceof F:___" + (xx instanceof F)); // true
console.log("xx instanceof G:___" + (xx instanceof G)); // true

如果出于某种原因你想让所有东西都包含更多,你可以使用 IIFE:

//test in chrome_v36 only
var G = (function() {
   var g = function() {
   };

   g.prototype.g1 = function() {};

   return g;
})();

var E = (function () {
    var e = function() {
    };

    e.prototype = Object.create(G.prototype); 
    e.prototype.e2 = function() {};

    return e;
})();

var F = (function () {
    var f = function() {
    };

    f.prototype = Object.create(E.prototype); 
    f.prototype.f3 = function() {};

    return f;
})();

但是,我真的看不出这样做有什么好处。至少对于这个简单的例子不是。

关于javascript __proto__ 不会产生与 "prototype"继承相同的效果,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26355095/

相关文章:

javascript - 如何控制这些组件?

java - 派生类的类变量的初始化/实例化和调用基类构造函数的顺序

java - Hibernate继承的策略是什么

javascript - XULrunner 添加不安全 : before links when using Angular

javascript - knockout 中的 foreach 绑定(bind)

javascript - 仅当 contentEditable div 更改时才显示元素

c++ - 为什么两个指针值不相同?

java - 从内存中清理 Spring Prototype-beans 澄清情况

jquery - 在 jQuery 中扩展原型(prototype)时如何保持对 this 关键字的控制?

javascript - 为什么在 JavaScript 对象中使用公共(public)方法?