具有多种复杂类型的数组

时间:2017-06-22 16:56:57

标签: typescript

有一个question on SO关于创建具有不同类型的数组,但我想创建一个具有多种复杂类型的数组。链接到问题的答案建议使用联合类型,但我不认为这对于复杂类型就足够了,正如typescript documentation所说

If we have a value that has a union type, we can only access members that are common to all types in the union. 

我想创建一个Reports数组。然而,一些报告具有彼此不同的属性,并且还有几个共同点。我担心如果我在下面的代码中创建它,那么我可能无法访问子报表上的不同属性。

在Typescript中创建复杂类型数组的推荐方法是什么?

interface Reports extends Array<Report>{}

interface Report {
    id: number; 
    timestamp: number;
    type: string;
    subreport: SubReportA | SubReportB | SubReportC
}



interface SubReportA {
values: []
}
interface SubReportB {
random_property: number;
other_random_name: number;
}
interface SubReportC{
values: [];
name: string;
}

1 个答案:

答案 0 :(得分:2)

这将是discriminated unions的用例。首先,我们需要一个用于各种子报告的基础接口。我还将添加一个区分字段kind,它只能假定编译时“A”,“B”和“C”中已知的特定值。

interface SubReport {
    kind: "A" | "B" | "C";
}

此时,我们可以使接口分别指定一个字符串文字:

interface SubReportA {
  kind: "A";
  values: []
}

interface SubReportB {
  kind: "B";
  random_property: number;
  other_random_name: number;
}

interface SubReportC{
  kind: "C";
  values: [];
  name: string;
}

如果需要,可以将相同的推理应用于原始Report类型。我不确定报告的“类型”字段是否应该是一个鉴别器,但如果它是,它可以移动到子报告对象。

此外,如上面的链接所述,一旦您在鉴别器上进行测试,受歧视的联合允许您检索特定字段。

if (subreport.kind === 'B') {
  console.log(subreport.random_property);
}