【问题标题】:Typescript generic return value inference issue打字稿通用返回值推断问题
【发布时间】:2020-08-06 15:56:52
【问题描述】:

我不确定这是 TS 中的错误还是他们认为不受支持的功能。 MVE:

interface ColumnOptions<R> {
  valueFormatter(params: R): string;
  valueGetter(params: string): R;
}

const getColumn = function<R>(options: ColumnOptions<R>) {};

getColumn({
  valueFormatter: params => 'hello',
  valueGetter: params => ({
    nr: 1,
    str: 'hello',
  }),
});

这是针对 Ag-grid 列定义的,目的是推断valueFormatter 的参数来自valueGetter 的返回类型。 valueFormatter(R)的参数在上述情况下被推断为unknown,但是如果我显式键入或删除valueGetter的参数,像这样:

getColumn({
  valueFormatter: params => 'hello',
  valueGetter: () => ({
    nr: 1,
    str: 'hello',
  }),
});

它正确地推断出 R。这就是让我认为它可能是 TS 中的错误的原因,但也许它只是不受支持,如果是这种情况,我不想在 GitHub 上打开问题。通过 TS 3.8、3.7、3.5 和 3.0 测试

【问题讨论】:

  • 我认为params 在第一种情况下是any,因此valueGetter(params: string): R 不匹配valueGetter(params: any): infer
  • 如果我没有明确输入valueGetter 声明,它会正确推断参数的类型为字符串,来自ColumnOptions

标签: javascript typescript type-inference


【解决方案1】:

我的理解,您的代码创建了一个循环依赖对。

R 可以从任一函数中推断为实体实例类型,然后用作引用以推断另一个函数的函数签名,如果它不完整或未知.

但要让它发挥作用,您需要首先提供至少一种实体类型,以打破循环。当您从valueGetter 中删除param 时会发生这种情况,因为您取消了对TS 推断参数类型的请求,从而将valueGetter 函数呈现为完整的实体类型。因此,返回类型可以用作R 的推断类型。

如果您为 params: string 提供显式类型,则以下内容也可以使用

getColumn({
  valueFormatter: params => 'hello',
  valueGetter: (params: string) => ({
    nr: 1,
    str: 'hello',
  }),
});

【讨论】:

    猜你喜欢
    • 2020-01-10
    • 1970-01-01
    • 2022-01-25
    • 1970-01-01
    • 2020-08-27
    • 1970-01-01
    • 2020-01-17
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多