Reputation: 1525
interface Interface {
a: number;
}
let var1: Interface = {
a: 0
};
const temp = {
a: 1,
b: 4
};
var1 = temp; // Compiler is fine with this
const var2: Interface = {
a: 2
};
var2.b = 3; // This won't compile
Am I the only one that finds this to be an inconsistency in the way the compiler behaves?
In the first scenario, the compiler doesn't care that the extra b
property ends up in the var1
variable.
Yet in the second scenario, the compiler won't permit var2
to have the extra property.
Why does this inconsistency exist?
Is it feasible to eliminate the inconsistency by either:
?
I appreciate that the current behaviour (consistent or inconsistent, depending on your perspective) has arisen because of trade-offs and is now widely adopted.
Yet is there a way (or is it feasible to provide a means) to opt-into preventing scenario 1 in certain cases?
I think what I'm looking for is kind of nominal typing behaviour, rather than structural.
I appreciate that TypeScript made the decision early on to provide structural typing, but I wonder about the feasibility (being a layperson in field of language design), of providing portions of both (structural and nominal).
This question was created with TypeScript version 2.2.1 in mind.
Upvotes: 1
Views: 135
Reputation: 164307
The reason that the first scenario is fine with the compiler is that typescript is based on structural subtyping and the structure of temp
satisfies the interface Interface
.
However, if you try to access the b
property then the compiler will complain:
console.log(var1.b); // error: Property 'b' does not exist on type 'Interface'
The error message is the same as with your 2nd scenario and that's how it is indeed consistent.
Here's an example of how it's useful:
interface Interface {
a: number;
}
interface BetterInterface {
a: number;
b: number;
}
function fn(a: Interface) { }
let a: BetterInterface = {
a: 0,
b: 0
};
fn(a);
Notice that BetterInterface
doesn't extend Interface
, but the compiler infers that from the structure of the object.
Upvotes: 4