【问题标题】:TypeScript error when passing parameters between functions在函数之间传递参数时出现 TypeScript 错误
【发布时间】:2019-05-08 10:42:35
【问题描述】:

此模式引发 TypeScript 错误:

'(string | number)[]' 类型的参数不能分配给参数 'string[] 类型 |数字[]'

function foo(value: string | number) {
  return bar([value]); // <- TypeScript error
}

function bar(valueList: string[] | number[]) {
  ..does something...
}

我理解这是因为 TypeScript 编译器会将其视为一个包含字符串和数字的数组。

有没有一种类型安全的方法来完成这个?我只能想投给any[],感觉很糟糕:

function foo(value: string | number) {
  const valueList: any[] = [value];
  return bar(valueList);
}

【问题讨论】:

  • 你注意到string和string[]的区别了吗?

标签: javascript typescript


【解决方案1】:

一种方法是declaration merging;为你的函数定义两个独立的接口(见function types),然后是它的一个实现:

interface Foo {
    (value: string): void;
}

interface Foo {
    (value: number): void;
}

const foo: Foo = function (value) {
  return bar([value]);
}

这将使两种类型分开,因为在任何给定时间只能调用其中一个接口。

【讨论】:

  • 有什么原因,你没有使用这样的东西:function foo(value: string);函数 foo(值:数字); function foo(value: any) { return bar([value]); }
  • @ChristophLütjen 我不知道你可以那样做!
  • 谢谢,不确定它是否已被弃用或单独的接口是否有其他好处 ;-)
【解决方案2】:

这受到 jonrsharpe 的回答的启发,但它没有使用单独的接口,而是使用函数重载。

函数重载允许我们为单个实现指定多个签名:https://www.typescriptlang.org/docs/handbook/functions.html#overloads

function foo(value: string);
function foo(value: number);
function foo(value: any) {
    return bar([value]);
}

function bar(valueList: number[] | string[]) {
}

【讨论】:

    【解决方案3】:

    另一个答案很好(我赞成),但我个人会选择

    return bar([value] as string[] | number[]);
    

    尤其是,如果我时间不够的话。这并不意味着它是错误的或骇人听闻的,您只是在暗示(在这种情况下)Typescript 有点愚蠢。

    附:正如@paleo 提到的,这不是完全类型安全的。

    【讨论】:

    • 您的解决方案并不是真正的类型安全,因为您可以编写:function foo(value: string | boolean) { return bar([value] as string[] | number[]); } (使用布尔值作为参数)。
    • 就个人而言,我避免过于冗长的解决方案。我只会使用as any,直到下一版本的 TypeScript 正确推断出这种情况。也许还可以在 GitHub 上开一张票。但我不建议这个答案,因为害怕投票。 ;)
    • @Paleo 同意一切。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-06-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-08-01
    • 1970-01-01
    相关资源
    最近更新 更多