2017-09-14 63 views
4

對於我的新小項目,我決定使用打字稿,原因不外乎讓自己感覺像編程c在顯着的類固醇上,顯然我付出了代價。Typescript接口的實現對索引簽名沒有任何影響

我有一個接口,右側

export default interface DataObject { 
    [key: string]: any 
}; 

按理說它是讓我和字符串鍵和任何值定義的對象。然後,我實現它

import DataObject from "./data-object"; 

export default class Model implements DataObject { 

    constructor(data: DataObject = {}) { 
    Model.fill(this, data); 
    } 

    static fill(model: Model, data: DataObject) { 
    for (let prop in data) { 
     model[prop] = data[prop]; 
    } 
    } 
} 

現在,我得到這個錯誤

元素隱含有「任意」類型,因爲類型「模式」有沒有索引簽名

在這line

 model[prop] = data[prop]; 

但是,如果我修改我的模型以包含簽名

import DataObject from "./data-object"; 

export default class Model implements DataObject { 

    [key: string]: any; 

    ... 
} 

然後沒有錯誤。

爲什麼界面簽名對我的班不起作用?

回答

1

我覺得接口對實現沒有影響。如果您將其更改爲類並將其擴展,則會按預期工作。這是因爲您可以通過其他方式實現索引,如屬性,請參閱示例(在Playground中)。

interface DataObject { 
    foo: any; 
    bar: any; 
    [key: string]: any; 
}; 

class Model implements DataObject { 

    private _bar: string = null; 
    public get bar(): string { 
     return this._bar; 
    } 
    public set bar(value: string) { 
     this._bar = value; 
    } 

    constructor(data: DataObject = {}) { 
     this.foo = "bar"; // error 
     this.bar = "foo"; // no error 
     Model.fill(this, data); 
    } 

    static fill(model: Model, data: DataObject) { 
     for (let prop in data) { 
      model[prop] = data[prop]; // error 
     } 
    } 
} 

class DataObject2 { 
    foo: any; 
    bar: any; 
    [key: string]: any; 
}; 

class Model2 extends DataObject2 { 

    constructor(data: DataObject2 = { foo: "", bar: "" }) { 
     super(); 
     this.foo = "bar"; // no error 
     this.bar = "foo"; // no error 
     Model2.fill(this, data); 
    } 

    static fill(model: Model2, data: DataObject2) { 
     for (let prop in data) { 
      model[prop] = data[prop]; // no error 
     } 
    } 
} 
+0

但這是如何有意義?接口不應該能夠首先定義屬性,但是既然他們這樣做,爲什麼這些類不會繼承簽名?沒有價值? –

+0

他們沒有定義。他們只是說「如果你實施我,就必須有財產」。只有語法看起來相同。在TypeScript中,你可以「實現」或「擴展」某些東西。類可以是「擴展」,接口(和類)可以​​是「實現」。 – Magu