将联合类型与不接受参数作为对象的函数一起使用

时间:2019-02-19 08:16:28

标签: typescript types union-types

下面是一个使用联合类型的函数。

type Shape = 
  { kind: 'circle', radius: number } |
  { kind: 'rectangle', w: number, h: number }

const getArea = (shape: Shape) => {     // this works
  switch(shape.kind) {
    case 'circle':
      return Math.PI * shape.radius ** 2
    case 'rectangle':
      return shape.w * shape.h
  }
  throw new Error('Invalid shape')
}

getArea({ kind: 'circle', radius: 10 })

它接受参数作为对象,因此可以正常工作。

但是当函数不接受参数作为对象时,我该怎么做。请参考下面的示例

type Shape = 
  { (kind: 'circle', ...args: [number]) } |
  { (kind: 'rectangle', ...args: [number, number]) }

const getArea: Shape = (kind, ...args) => {     // this doesn't work
  switch(kind) {
    case 'circle':
      return Math.PI * args[0] ** 2
    case 'rectangle':
      return args[0] * args[1]
  }
  throw new Error('Invalid shape')
}

getArea('circle', 10)
getArea('rectangle', 5, 5)

我也可以这样写

const getArea: Shape = (kind: 'update' | 'reset', ...args: [number] | [number, number]) => {

但不会给我带来完全的安全性。如第一个示例所示,我希望当种类改变时args改变。

对于这种问题,是否有其他方法?

1 个答案:

答案 0 :(得分:1)

您可以这样写

const getArea = (...[key, ...args]: ['circle', number] | ['rectangle', number, number]) => {
    switch (key) {
        case 'circle':
            return Math.PI * args[0] ** 2
        case 'rectangle':
            return args[0] * args[1]
    }
    throw new Error('Invalid shape')
}

const getArea = (...args: ['circle', number] | ['rectangle', number, number]) => {
    switch (args[0]) {
        case 'circle':
            return Math.PI * args[1] ** 2
        case 'rectangle':
            return args[1] * args[2]
    }
    throw new Error('Invalid shape')
}