当将 typeof typeguard 分配给一个变量时,是否无法工作?

13 浏览
0 Comments

当将 typeof typeguard 分配给一个变量时,是否无法工作?

当我使用如下的typeof时,我遇到了一个错误。

function func (variable: number | string) {
    const is_number = (typeof variable === 'number');
    let variable2: number,
        variable3: string;
    if (is_number)
        variable2 = variable;
        => 类型 'string | number' 不能赋值给类型 'number'。
           类型 'string' 不能赋值给类型 'number'。
    else
        variable3 = variable;
        => 类型 'string | number' 不能赋值给类型 'string'。
           类型 'number' 不能赋值给类型 'string'。
}

然而,以下的代码没有出错:

function func (variable: number | string) {
    let variable2: number,
        variable3: string;
    if (typeof variable === 'number')
        variable2 = variable;
    else
        variable3 = variable;
}

测试链接

我是否总是要像上面那样使用它?还是我使用了错误的部分?

谢谢阅读 🙂

0
0 Comments

问题的原因是,当使用typeof关键字进行类型保护时,将其赋值给变量时,类型保护就不起作用了。这是因为typeof返回的是一个字符串,而不是一个类型。

解决方法是使用一个辅助函数isNumber来实现类型保护。这个函数使用x is y的语法,将一个断言传递给TypeScript编译器。以下是isNumber函数的示例代码:

const isNumber = (subject: any): subject is number => {
    return typeof subject === 'number';
};

isNumber函数中,TypeScript可以从返回的布尔值中推断出类型number。现在,如果在自己的func函数中使用这个辅助函数,就可以解决问题了。

function func (variable: number | string) {
    let variable2: number;
    let variable3: string;
    if (isNumber(variable)) {
        variable2 = variable;
    } else {
        variable3 = variable;
    }
}

由于if块只有在isNumber(variable)返回true时才会执行,TypeScript现在会假设subject is number。下面的伪代码演示了TS对上述代码的解释:

if (variable is number) {
    // ...
}

以上就是解决问题的方法。此外,还可以参考这个Stack Overflow的回答,进一步了解类型保护的构造。

0