Oli*_*Ash 7 generics typescript
给定一个函数,该函数接收相同泛型的两个参数:
declare const fn: <T>(t1: T, t2: T) => any;
Run Code Online (Sandbox Code Playgroud)
我试图推断调用此函数时TypeScript的不同行为。
当两个参数都是不同的原语时:
fn(1, 'foo'); // Error due to different types
Run Code Online (Sandbox Code Playgroud)
当两个参数都是不同的对象时:
fn({ foo: 1 }, { bar: 1 }) // No error and return type is union of different types
Run Code Online (Sandbox Code Playgroud)
这两种用法为什么没有相同的行为?我希望他们的行为都一样。要么:
其次,如果传入的参数之一是变量(而不是内联对象文字),则TypeScript的行为会再次不同:
fn({ foo: 1 }, { bar: 1 }) // No error and return type is union of different types
const obj = { foo: 1 };
fn(obj, { bar: 1 }) // Error due to different types
Run Code Online (Sandbox Code Playgroud)
同样,这两种用法为什么没有相同的行为?我希望这两种情况的行为相同。
此行为引人注目的用例来自这样的示例,其中您有一些候选类型集,没有一个是其他类型的超类型,但预期的推断类型参数 ( { a?: number, b?: number, c?: number }
) 非常明显:
declare const fn: <T>(t1: T, t2: T, t3: T) => any;
fn({ a: 0, b: 1 }, { b: 2, c: 3 }, { a: 4, c: 5 });
Run Code Online (Sandbox Code Playgroud)
当参数不是对象文字时,为什么不会发生这种情况?
当您与某种 type进行绑定 时,TypeScript 无法*知道 by 指向的对象具有确切的类型- 它可能具有更多未在 中声明的属性,但最终通过子类型关系绑定到。这在实践中很常见。foo
T
foo
T
T
foo
因此,在 OP 的示例中,推断类型{ foo?: number, bar?: number }
是不合理的,因为obj
可能指向具有bar
type 属性的对象string
。
*
您可以在 s 周围添加更多特殊情况,const
这些特殊情况是使用未对其他内容进行类型断言的对象文字初始化的,但这只会使事情变得更加不一致
归档时间: |
|
查看次数: |
93 次 |
最近记录: |