简体   繁体   中英

Type declaration works for object literal, but not for class implementation

I want a type to represent a coordinate. The type I have have applied to an interface works for an object but not a class.

type ICoord = [number, number]

type MyInterface = {
    a: ICoord
}

var obj: MyInterface = { // works
    a: [0, 0]
}

class C implements MyInterface { // gets below compilation error
    a = [0, 0]
}

Property 'a' in type 'C' is not assignable to the same property in base type 'MyInterface'. Type 'number[]' is missing the following properties from type '[number, number]': 0, 1

Why can't I assign [0, 0] to a ?

[TypeScript Playground]

The type of a is being inferred as number[] which is not assignable to the tuple [number, number] . Explicitly defining the type as ICoord for a appears to work:

type ICoord = [number, number];

type MyInterface = {
  a: ICoord;
}

class C implements MyInterface {
  a: ICoord = [0, 0];
}

TypeScript Playground

This has to do with contextual typing.

Typescript usses the expected type of an expression ( MyInterface in this case) to make better inferences about object literals (also about function parameters). This is why assigning an object literal works well and the array literals is typed as a tuple type.

For classes things are a bit different. The implements clause is just used to check that the class correctly implements the interface AFTER the class has been independently typed. The implements keyword does not create any contextual typing for any of the class members. This is also the reason you have to specify function parameters types even if they would be obvious from the interface or base class.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM