TypeScriptでのクラス型チェック


240

ActionScriptでは、is演算子を使用して実行時に型を確認できます

var mySprite:Sprite = new Sprite(); 
trace(mySprite is Sprite); // true 
trace(mySprite is DisplayObject);// true 
trace(mySprite is IEventDispatcher); // true

変数(拡張または)が特定のクラスまたはTypeScriptとのインターフェースであるかどうかを検出することはできますか?

言語仕様では何も見つかりませんでした。クラス/インターフェースを操作するときは、そこにあるはずです。

回答:


319

4.19.4 instanceof演算子

instanceofオペレータは、タイプ「の関数」インターフェイスタイプのいずれかまたはサブタイプであることが、型のいずれかであることがオブジェクト型、または型パラメータの種類、及び右オペランドを左オペランドを必要とします。結果は常にブールプリミティブタイプになります。

だからあなたは使うことができます

mySprite instanceof Sprite;

この演算子はActionScriptにもありますが、ここでは使用しないでください。

is演算子はActionScript 3.0の新機能で、変数または式が特定のデータ型のメンバーであるかどうかをテストできます。以前のバージョンのActionScriptでは、instanceof演算子がこの機能を提供していましたが、ActionScript 3.0では、instanceof演算子を使用してデータ型のメンバーシップをテストしないでください。手動の型チェックには、instanceof演算子の代わりにis演算子を使用する必要があります。式x instanceof yは、xのプロトタイプチェーンにyが存在するかどうかをチェックするだけです(ActionScript 3.0では、プロトタイプチェーンは継承階層)。

TypeScriptにinstanceofも同じ問題があります。それはまだ開発中の言語なので、そのような施設の提案を述べることをお勧めします。

以下も参照してください。


54

TypeScriptには、実行時に変数の型を検証する方法があります。タイプ述語を返す検証関数を追加できます。したがって、if関数内でこの関数を呼び出すことができ、そのブロック内のすべてのコードが、想定している型として安全に使用できることを確認してください。

TypeScriptドキュメントの例:

function isFish(pet: Fish | Bird): pet is Fish {
   return (<Fish>pet).swim !== undefined;
}

// Both calls to 'swim' and 'fly' are now okay.
if (isFish(pet)) {
  pet.swim();
}
else {
  pet.fly();
}

詳しくは、https//www.typescriptlang.org/docs/handbook/advanced-types.htmlをご覧ください。


29
これは実行時の型チェックではなく、オブジェクトに特定のプロパティがあるかどうかをチェックするだけです。これはユニオンタイプに適しているため、この特定のケースで機能しますが、このようなすべての「isThingy」を作成することは実際にはできません。また、魚と鳥の両方が泳ぐことができるなら、あなたは運命にあります。私はあなたがすることができるので、信頼性の型チェックを持つhaXeの使用していてくれてうれしいStd.is(pet, Fish)のインターフェイスなどの種類で動作します、
マーク・Knolの

4
この回答は役に立ちましたが、もう少し正確になるように微調整できると思います。isFish自身が作成された述語であり、その体はワンライナーの述語である必要はありません。これの利点は、コンパイラーがコンパイル時に適切な可能な関数を理解しますが、内部のコードisFishは実行時に実行されることです。instanceofたとえば、ガードにステートメントを含めることもできますreturn pet instanceof Fish(それがクラスであり、インターフェイスではないと想定)。ただし、コンパイラがinstanceof直接理解するため、これは不要です。

4
これは「ユーザー定義型ガード」とも呼ばれます。basarat.gitbooks.io/ typescript / content / docs / types /…を
Julian

@MarkKnolこれは実際にはランタイムチェックですが、typescriptに推測された型を理解する機能ももたらします(つまり、実行時にテストするため、これはXまたはY型であると信頼できます)。
Flavien Volken

3
(pet as Fish)tslinterはについて不平を言うので、使用を検討してください(<Fish>pet)tslint docを
ブライアン

1

instanceofこれには演算子を使用できます。MDNから:

instanceof演算子は、コンストラクターのプロトタイププロパティがオブジェクトのプロトタイプチェーンのどこかに現れるかどうかをテストします。

プロトタイプとプロトタイプチェーンがわからない場合は、調べることを強くお勧めします。また、これはJS(TSはこの点で同様に機能します)の例であり、概念を明確にする可能性があります。

    class Animal {
        name;
    
        constructor(name) {
            this.name = name;
        }
    }
    
    const animal = new Animal('fluffy');
    
    // true because Animal in on the prototype chain of animal
    console.log(animal instanceof Animal); // true
    // Proof that Animal is on the prototype chain
    console.log(Object.getPrototypeOf(animal) === Animal.prototype); // true
    
    // true because Object in on the prototype chain of animal
    console.log(animal instanceof Object); 
    // Proof that Object is on the prototype chain
    console.log(Object.getPrototypeOf(Animal.prototype) === Object.prototype); // true
    
    console.log(animal instanceof Function); // false, Function not on prototype chain
    
    

この例のプロトタイプチェーンは次のとおりです。

動物> Animal.prototype> Object.prototype

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.