在TypeScript中将类型永不与接口/类实现一起使用

时间:2018-11-02 08:40:06

标签: typescript class interface

我想使用打字稿从不类型,以确保我已经检查了接口的所有可能的实现。 Here is the code:

interface MyInterface {
    a: string;
    b: number;
}

class MyClass1 implements MyInterface {
    a: string;
    b: number;

    constructor() { }
}

class MyClass2 implements MyInterface {
    a: string;
    b: number;

    constructor() { }
}

function foo(arg: MyInterface) {
    if (arg instanceof MyClass1) {

    } else if (arg instanceof MyClass2) {

    } else {
        assertNever(arg);
    }
}

function assertNever(value: never): never {
  throw Error(`Unexpected value '${value}'`);
}

但是我得到了错误:'MyInterface'类型的参数不能分配给'never'类型的参数。

有什么办法可以解决这个问题吗?

2 个答案:

答案 0 :(得分:1)

您可以使用assertNever方法来确保处理所有案件(我猜这是您想做的)。问题是您需要所有可能性的结合而不是使用接口。 Typescript无法知道接口的所有实现都是什么,因此您的类型保护人员不会缩小参数的类型。

这将按您期望的那样工作:

function foo(arg: MyClass1 | MyClass2) {
    if (arg instanceof MyClass1) {

    } else if (arg instanceof MyClass2) {

    } else {
        assertNever(arg);
    }
}

答案 1 :(得分:0)

我认为你永远不会误会。

docs

  

never类型是每种类型的子类型,并且可以分配给每种类型;但是,任何类型都不是(永远不会除外的)永不的子类型或可分配给它的子类型。甚至任何东西都无法分配给永不。

您无法将值分配给never 由于您的类型声明为assertNever(value: never),因此在调用assertNever(arg);

时向它分配变量时将引发错误。

只需将其更改为assertNever(value: any): never即可解决该错误。 (或根据需要指定更具体的类型)