Select 基于 TypeScript 中第一个参数的函数重载
Select a function overload based upon the first argument in TypeScript
我想创建一个函数 f
,它接受 Box<T>
作为它的第一个参数,第二个类型为 T
的参数是可选的,如果(且仅当! ) T extends null
.
下面是 f
的调用方式:
let _ = new Box(null)
let o = new Box({})
f(_, null) // ✅
f(o, {}) // ✅
f(_) // ✅
f(o) // ❌ (should not compile)
这是我(试图)定义 f
:
class Box<V = any> {
constructor(public v: V) {}
}
type _ = null
type O = object
function f<V extends _>(b: Box<V>, v?: V): void
function f<V extends O>(b: Box<V>, v: V): void
function f(b: Box, v?: any) {}
乍一看似乎可行。但是有一个问题! f(o)
的错误报告如下:
Argument of type 'Box<{}>' is not assignable to parameter of type 'Box<null>'.
当我希望 f
的用户实际看到的错误是:
Expected 2 arguments, but got 1.
似乎 TypeScript 优先 select 重载第二个参数是可选的。当 T
不扩展 null 时,如何使它成为 select 另一个重载?或者以其他方式实现我的目标?
如果您在剩余参数中使用条件类型来基本上更改基于 V
:
的最后一个参数的可选性,您会得到想要的错误
function f<V>(b: Box<V>, ...a: V extends null ? [v?: V]: [v:V]): void
function f(b: Box, v?: any) {}
我想创建一个函数 f
,它接受 Box<T>
作为它的第一个参数,第二个类型为 T
的参数是可选的,如果(且仅当! ) T extends null
.
下面是 f
的调用方式:
let _ = new Box(null)
let o = new Box({})
f(_, null) // ✅
f(o, {}) // ✅
f(_) // ✅
f(o) // ❌ (should not compile)
这是我(试图)定义 f
:
class Box<V = any> {
constructor(public v: V) {}
}
type _ = null
type O = object
function f<V extends _>(b: Box<V>, v?: V): void
function f<V extends O>(b: Box<V>, v: V): void
function f(b: Box, v?: any) {}
乍一看似乎可行。但是有一个问题! f(o)
的错误报告如下:
Argument of type 'Box<{}>' is not assignable to parameter of type 'Box<null>'.
当我希望 f
的用户实际看到的错误是:
Expected 2 arguments, but got 1.
似乎 TypeScript 优先 select 重载第二个参数是可选的。当 T
不扩展 null 时,如何使它成为 select 另一个重载?或者以其他方式实现我的目标?
如果您在剩余参数中使用条件类型来基本上更改基于 V
:
function f<V>(b: Box<V>, ...a: V extends null ? [v?: V]: [v:V]): void
function f(b: Box, v?: any) {}