このコードを書きました
interface Foo {
abcdef: number;
}
let x: Foo | string;
if (x instanceof Foo) {
// ...
}
しかし、TypeScriptは私にこのエラーを与えました:
'Foo' only refers to a type, but is being used as a value here.
なぜこうなった? instanceof
は、値に特定の型があるかどうかを確認できると思っていましたが、TypeScriptはこれを好まないようです。
問題は、 instanceof
がJavaScriptからのコンストラクトであり、JavaScriptではinstanceof
が右側のオペランドにvalueを期待していることです。 。具体的には、x instanceof Foo
で、JavaScriptはFoo.prototype
がx
のプロトタイプチェーンのどこかに存在するかどうかを確認するためにランタイムチェックを実行します。
ただし、TypeScriptでは、interface
sには出力がありません。つまり、Foo
もFoo.prototype
も実行時に存在しないため、このコードは間違いなく失敗します。
TypeScriptは、これがnever動作する可能性があることを伝えようとしています。 Foo
は単なる型であり、値ではありません!
instanceof
の代わりに何ができますか?」type guardsおよびuser-defined type guards を調べることができます。
interface
からclass
に切り替えた場合はどうなりますか?」interface
からclass
に切り替えたいと思われるかもしれませんが、TypeScriptの構造型システム(主にshape based)特定のクラスと同じ形状を持つオブジェクトを作成できます。
class C {
a: number = 10;
b: boolean = true;
c: string = "hello";
}
let x = new C()
let y = {
a: 10, b: true, c: "hello",
}
// Works!
x = y;
y = x;
この場合、同じタイプのx
とy
がありますが、どちらかでinstanceof
を使用しようとすると、反対の結果が得られます。そのため、instanceof
はreallyではありません。TypeScriptで構造型を利用している場合、型について詳しく説明しません。
ダニエル・ローゼンワッサーは正しくてダンディかもしれませんが、彼の答えを修正したい気がします。 xのインスタンスを確認することは完全に可能です。コードスニペットを参照してください。
ただし、x = yを割り当てるのも同様に簡単です。 yはCの形状しかなかったため、xはCのインスタンスではなくなりました。
class C {
a: number = 10;
b: boolean = true;
c: string = "hello";
}
let x = new C()
let y = {
a: 10, b: true, c: "hello",
}
console.log('x is C? ' + (x instanceof C)) // return true
console.log('y is C? ' + (y instanceof C)) // return false