繁体   English   中英

解构 arguments 下可选 function arguments 在 typescript 抛出错误

[英]Destructured arguments under optional function arguments in typescript throw error

interface Type1 {
  attr1: string;
  attr2: string;
}
interface Type2 {
  attr1: string;
  attr2: string;
  attr3: string; // extra attribute
}

function fn(config: Type1 | Type2): void {
  // Property 'attr3' does not exist on type 'Type1 | Type2'.ts(2339)
  const { attr1, attr2, attr3 } = config;
  console.log(attr1);
  console.log(attr2);
  console.log(attr3);
}

错误代码显示之前。 而且我知道有一个解决方案可以在attr3添加可选属性。 但就我而言,这个解决方案并不好。 因为事实上只有Type1Type2两种情况。 总之,可选方式不是可读性。 如何以高级方式修复它?

您可以简单地检查attr3是否存在于 object

function fn(config: Type1 | Type2): void {
  if ('attr3' in config) {
    const {
      attr1,
      attr2,
      attr3
    } = config;
  } else {
    const {
      attr1,
      attr2
    } = config;
  }
}

或者您可以使用自定义类型保护

function IsType2(config: Type1 | Type2): config is Type2 {
  return (config as Type2).attr3 !== undefined;
}

function fn(config: Type1 | Type2): void {
  if (IsType2(config)) {
    const {
      attr1,
      attr2,
      attr3
    } = config;
  } else {
    const {
      attr1,
      attr2
    } = config;
  }
}

或者如果我们真的只想解构一次,我们可以创建一个连接类型,尽管我们会强制类型而不是推断它。

function fn(config: Type1 | Type2): void {
  const {
    attr1,
    attr2,
    attr3
  } = config as Type1 & Type2;
}

据我所知,没有办法直接解构联合类型

如果您想在缺少attr3属性时获得与js代码相同的结果,您可以将配置类型转换为类型的交集:

interface Type1 {
  attr1: string;
  attr2: string;
}
interface Type2 {
  attr1: string;
  attr2: string;
  attr3: string; // extra attribute
}

type UnionToIntersection<U> = 
  (U extends any ? (k: U)=>void : never) extends ((k: infer I)=>void) ? I : never

function fn(config: Type1 | Type2): void {
  // Property 'attr3' does not exist on type 'Type1 | Type2'.ts(2339)
  const { attr1, attr2, attr3 } = config as UnionToIntersection<Parameters<typeof fn>[0]>;
  console.log(attr1);
  console.log(attr2);
  console.log(attr3);
}

fn({ attr1: '', attr2: '' })

或者只是... = config as Type1 & Type2; 如果你不介意一些不灵活。

TS游乐场

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM