TS 中如何编写有可选参数的函数重载?

先看下这段代码:

type App = {
  name: string
  description: string
}

const apps = [] as App[]

export function getApp(): App[]
export function getApp(name: string): App | undefined
export function getApp(name?: string) {
  if (name) {
    return apps.find(app => app.name === name)
  }
  return apps
}

这里定义了一个 getApp() 函数,如果不传入参数则返回所有的 App,传入第一个参数返回对应的 App

稍微验证一下:

const a = getApp() // App[] 类型,正确
const b = getApp('b') // App | undefined 类型,正确

嗯,看起来很对。然而如果这样写,问题就来了:

export function getAppAndLog(name?: string) {
  const app = getApp(name)
  console.log(app)
}

这里 getApp(name) 会报错:

(parameter) name: string | undefined
Argument of type 'string | undefined' is not assignable to parameter of type 'string'.
  Type 'undefined' is not assignable to type 'string'.ts(2345)
The call would have succeeded against this implementation, but implementation signatures of overloads are not externally visible.

如何解决这个错误呢?

阅读 2.7k
1 个回答

用了重载的话,函数调用的签名是这两个:

export function getApp(): App[]
export function getApp(name: string): App | undefined

而函数实现的签名无法在调用的时候直接使用

Then, we wrote a function implementation with a compatible signature. Functions have an implementation signature, but this signature can’t be called directly. Even though we wrote a function with two optional parameters after the required one, it can’t be called with two parameters!

因此这里你传入一个 string | undefined类型并不满足前面声明的两个签名,因此报错了,可以改成这样:

export function getApp(): App[]
export function getApp(name?: string): App | undefined
export function getApp(name?: string) {
  if (name) {
    return apps.find(app => app.name === name)
  }
  return apps
}
撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题