TypeScript - 检查 Class 是否实现了接口

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/37543588/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-09 07:09:10  来源:igfitidea点击:

TypeScript - Check if Class implements an Interface

typescript

提问by MarkLunney

I'm using an interface in TypeScript to define a function that is only available on some of the classes that extend the base class. This is a simplified version of the code I have so far:

我在 TypeScript 中使用一个接口来定义一个函数,该函数仅在扩展基类的某些类上可用。这是我到目前为止的代码的简化版本:

class Animal {
}

interface IWalkingAnimal {
    walk(): void;
}

class Dog extends Animal implements IWalkingAnimal {
}

class Cat extends Animal implements IWalkingAnimal {
}

class Snake extends Animal {
}

private moveAnimal(animal: Animal) {
    if (animal instanceof Cat || animal instanceof Dog) {
        animal.walk();
    }
}

Now, the trouble is I'll be adding more 'walking' animals so the moveAnimal functional will grow too large to be manageable. What I would like to do is something like this:

现在,问题是我将添加更多“行走”动物,因此 moveAnimal 函数会变得太大而无法管理。我想做的是这样的:

private moveAnimal(animal: Animal) {
    if (animal implements IWalkingAnimal ) {
        animal.walk();
    }
}

However the 'implements' check does not work, and I cannot find an equivalent to 'instanceof' when using interfaces. In Java it seems that the use of 'instanceof' would work here, but TypeScript will not allow this.

但是,“实现”检查不起作用,并且在使用接口时我找不到与“instanceof”等效的东西。在 Java 中,'instanceof' 的使用似乎可以在这里工作,但 TypeScript 不允许这样做。

Does such a thing exist in TypeScript, or is there a better approach here? I am using the TypeScript 1.8.9.

TypeScript 中是否存在这样的东西,或者这里有更好的方法吗?我正在使用 TypeScript 1.8.9。

回答by Thilo

Unlike classes, interfaces exist only at compile-time, they are not included into the resulting JavaScript, so you cannot do an instanceofcheck.

与类不同,接口仅在编译时存在,它们不包含在生成的 JavaScript 中,因此您无法进行instanceof检查。

You could make IWalkingAnimala subclass of Animal (and use instanceof), or you could check if the object in question has a walkmethod:

您可以创建IWalkingAnimalAnimal 的子类(并使用instanceof),或者您可以检查有问题的对象是否有walk方法:

if (animal['walk']) {}

You can wrap this in a user defined type guard(so that the compiler can narrow the type when used in an ifstatement, just like with instanceof).

您可以将其包装在用户定义的类型保护中(以便编译器在if语句中使用时可以缩小类型,就像 with 一样instanceof)。

/**
* User Defined Type Guard!
*/
function canWalk(arg: Animal): arg is IWalkingAnimal {
   return (arg as IWalkingAnimal).walk !== undefined;
}


private moveAnimal(animal: Animal) {
    if (canWalk(animal)) {
        animal.walk();  // compiler knows it can walk now
    }
}