Ich habe mich gefragt, was zwischen Typenannotation variable: type
und Typ Behauptung Ausdruck als Typ
Typdeklaration variable: type
teilt dem Compiler mit, dass die Variable muss immer entsprechen dem deklarierten Typ der genaue Unterschied ist. Es wird von typechecker verwendet, wenn der Variablen ein Wert zugewiesen wird (der Wert muss mit dem deklarierten Typ kompatibel sein), und auch immer dann, wenn die Variable verwendet wird (der deklarierte Typ der Variablen muss mit der Art und Weise kompatibel sein, in der die Variable verwendet wird) jeder bestimmte Ort).
Die Typassertion überschreibt die integrierten Kompatibilitätsregeln. Sie können dem Compiler mitteilen, dass Sie wissen, dass der Wert tatsächlich dem Typ entspricht, den Sie in der Assertion angeben, und somit die Fehlermeldung über die Typinkompatibilität unterdrücken. Es gibt jedoch Grenzen - Sie können nicht einfach behaupten, dass die Variable einen beliebigen Typ hat (BTW gibt es any
Typ nur dafür). Wie Sie in der Frage zitiert, für Typen Behauptung zu arbeiten,
die Behauptung vom Typ S zu T ist erfolgreich, wenn entweder S ein Subtyp von T oder T ist ein Subtyp von S
Es funktioniert genau auf diese Weise in jedem Beispiel:
const foo3 = { n: '' } as Foo; // KO: "Property 's' is missing..."
hier zwei Typen: {n?: number, s: string}
und {n: string}
sind auf Kompatibilität geprüft - ob einer von ihnen kann in einer anderen umgewandelt werden. Es kann nicht so oder so gemacht werden: {n: string}
fehlt nicht-optional s
und n
hat den falschen Typ (muss number | undefined
sein); Auf andere Weise hat {n?: number, s: string}
einen falschen Typ für n
(muss string
sein).
Die vollständige Fehlermeldung ist
Type '{ n: string; }' cannot be converted to type 'Foo'.
Property 's' is missing in type '{ n: string; }'.
Wenn Strukturtyp Unverträglichkeit berichtet, der Compiler nur eine inkompatible Eigenschaft wählt in der Fehlermeldung zeigen - dass einer der drei oben genannten Unvereinbarkeiten sein könnte.
const foo4 = { n: '' as any } as Foo; // ok
Works weil {n?: number, s: string}
mit {n: any}
kompatibel ist: die erste mit dem zweiten zugeordnet werden - any
mit allem kompatibel ist und s
wird nur (im Grunde ignoriert, ein Wert ist kompatibel mit dem Typ, wenn es hat alle nicht-optionale Eigenschaften kompatibel mit deklarierten Typ)
const foo5 = { n: 1, x: 2 } as Foo; // KO: "Property 's' is missing..."
{n: number, x: number}
ist nicht zuordenbar {n?: number, s: string}
- s
fehlt, wie Compiler sagt:
Type '{ n: number; x: number; }' cannot be converted to type 'Foo'.
Property 's' is missing in type '{ n: number; x: number; }'.
const foo6 = { s: '', x: 2 } as Foo; // ok
Works weil {s: string, x: number}
zu {n?: number, s: string}
zuordenbar ist: s
ist OK, fehlt n
OK ist, weil es als optional deklariert wird, Extra x
wird ignoriert
const foo7 = { s: 1, x: 2 } as Foo; // KO: "Types of property 's' are incompatible."
Typ s
ist unvereinbar:
Type '{ s: number; x: number; }' cannot be converted to type 'Foo'.
Types of property 's' are incompatible.
Type 'number' is not comparable to type 'string'.
Dies ist interessant, weil es Fehler aus, wenn Sie den falschen Typs für eine Eigenschaft zur Verfügung stellen, aber die Fehlermeldung ist immer über eine andere Eigenschaft. Abgesehen davon, wenn die von Ihnen bereitgestellten Eigenschaftsnamen vom richtigen Typ sind, können andere Eigenschaften weggelassen oder hinzugefügt werden, was sinnvoll erscheint. –