簡體   English   中英

JavaScript:超類中的“this”指的是子類

[英]JavaScript: 'this' in superclass refers to subclass

我正在從子類調用超類方法。 當從子類調用時,超類方法中的“this”不再指代超類,而是指調用它的子類。 這會導致 inheritance 出現問題。

詳情如下:

在我的項目中,我使用 class 從注冊類型構造對象。 這些類型是從屬性中注冊的,或者是從基於已定義類型的模板中注冊的:

class A{

createObject(type) {
    let object = null;
    for (let i in this.objecttypes) {
        if (this.objecttypes[i].type == type) {
            if (this.objecttypes[i].template) {
                object = this.createObject(this.objecttypes[i].template);
                object.type = type;
            }
            else
                object = new TestObject(type);
            for (const aname in this.objecttypes[i].attributes)
                object.set(aname, this.objecttypes[i].attributes[aname]);
            //console.log("Object: "+JSON.stringify(object));
        }
    }
    return object;
}

}

這在超類中運行良好。 但是,我還構建了一個具有更用戶友好方法的子類。 在子類中,名為“createObject”的方法不返回創建的 object。 它存儲它並返回 object id:

class B extends A{

createObject(type,otherargs){
    let object=super.createObject(type);
    this.objects.set(object.id,object);
    /* do things with otherargs     */
    return object.id;
}

}

/* Method to test function. In test class */

templateObjects(){
    let container=this.getContainer();
    console.log("proto: "+JSON.stringify(Object.getPrototypeOf(container)));
    let tt=App.createObjectType("template1","",[{name:"attr0",value:1},{name:"attr1",value:2},{name:"attr2",value:3}]);
    let ut=App.createObjectType("test","template1",[{name:"attr3",value:66}]);
    container.addObjectType(tt);
    container.addObjectType(ut);
    let o0=container.createObject("template1");
    console.log("Object: "+JSON.stringify(o0));
    let o1=container.createObject("test");
    console.log("Object: "+JSON.stringify(o1));
}

    

當我現在嘗試從子類創建基於模板的對象時,超類代碼就到了這一點:

            if (this.objecttypes[i].template) {
                object = this.createObject(this.objecttypes[i].template);
                object.type = type;
            }

'this.createObject(...)' 調用導致調用子類的 createObject 方法,從而返回一個數字鍵,並且嘗試為其分配類型失敗。

我知道我可以例如重命名子類中的方法以避免問題,我可以發送 class object(“this”)作為參數或其他棘手的東西。

但是有沒有更直接、更慣用的方法來解決這個問題?

this是指 object,而不是 class。 在這種情況下,它是正常使用的B實例(即使在A中的代碼中——只有一個對象)。 由於 object 的createObject屬性來自B ,這就是您從this.createObject獲得的(無論該代碼出現在何處)。

但是還有一個更根本的問題:

當您子類化某些東西時,您是在說它是您子類化的東西的更專業的版本。 也就是說, B是專門A 這意味着BA A有一個特定的合同,例如它從它的createObject方法返回一個 object。 通過更改B中的返回類型,您將違反該合同。 B不再是A ,它是類似於A的東西,除了createObject

所以我建議不要這樣做,因為它違反了子類化規則之一。

可以A中的代碼調用AcreateObject版本,如下所示:

object = A.prototype.createObject.call(this, this.objecttypes[i].template);

但我強烈建議您不要這樣做。 :-) 相反,不要讓B違反A的合同。 對您在B中所做的事情使用不同的方法。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM