打字稿条件界面

时间:2020-04-30 12:14:50

标签: typescript oop interface

我有2个界面

interface i1 {
    x: number;
}

interface i2  {
    x: number;
    y: number;
    z: number
}

// ok
const o: i1 = {
    x: 1,
}

// ok
const o: i2 = {
    x: 1,
    y: 2,
    z: 3
}

我想指定,如果我的对象具有y字段,那么它也必须具有z字段

我正试图通过这种方式解决问题

    // expected error but everything is "fine"
    const o: i1 | i2 = {
        x: 1,
        y: 2,
    }

如果我没错,{ x: number, y: number }不应与i1i2中的任何一个匹配。

执行此操作的正确方法是什么?谢谢你们。

1 个答案:

答案 0 :(得分:2)

您需要使library(data.table) library(rlist) lst <- list(var1 = list(`0.1` = c(100, 10, 1, 0.1, 0.01), `0.2` = c(100, 20, 4, 0.8, 0.16), `0.3` = c(100, 30, 9, 2.7, 0.81), `0.4` = c(100, 40, 16, 6.4, 2.56), `0.5` = c(100, 50, 25, 12.5, 6.25), `0.6` = c(100, 60, 36, 21.6, 12.96), `0.7` = c(100, 70, 49, 34.3, 24.01), `0.8` = c(100, 80, 64, 51.2, 40.96), `0.9` = c(100, 90, 81, 72.9, 65.61)), var2 = list(`0.1` = c(10, 11, 11.1, 11.11, 11.111), `0.2` = c(10, 12, 12.4, 12.48, 12.496), `0.3` = c(10, 13, 13.9, 14.17, 14.251), `0.4` = c(10, 14, 15.6, 16.24, 16.496), `0.5` = c(10, 15, 17.5, 18.75, 19.375), `0.6` = c(10, 16, 19.6, 21.76, 23.056), `0.7` = c(10, 17, 21.9, 25.33, 27.731), `0.8` = c(10, 18, 24.4, 29.52, 33.616), `0.9` = c(10, 19, 27.1, 34.39, 40.951))) temp = lapply(lst, as.data.table) final = rlist::list.cbind( temp ) final #> var1.0.1 var1.0.2 var1.0.3 var1.0.4 var1.0.5 var1.0.6 var1.0.7 var1.0.8 #> 1: 1e+02 100.00 100.00 100.00 100.00 100.00 100.00 100.00 #> 2: 1e+01 20.00 30.00 40.00 50.00 60.00 70.00 80.00 #> 3: 1e+00 4.00 9.00 16.00 25.00 36.00 49.00 64.00 #> 4: 1e-01 0.80 2.70 6.40 12.50 21.60 34.30 51.20 #> 5: 1e-02 0.16 0.81 2.56 6.25 12.96 24.01 40.96 #> var1.0.9 var2.0.1 var2.0.2 var2.0.3 var2.0.4 var2.0.5 var2.0.6 var2.0.7 #> 1: 100.00 10.000 10.000 10.000 10.000 10.000 10.000 10.000 #> 2: 90.00 11.000 12.000 13.000 14.000 15.000 16.000 17.000 #> 3: 81.00 11.100 12.400 13.900 15.600 17.500 19.600 21.900 #> 4: 72.90 11.110 12.480 14.170 16.240 18.750 21.760 25.330 #> 5: 65.61 11.111 12.496 14.251 16.496 19.375 23.056 27.731 #> var2.0.8 var2.0.9 #> 1: 10.000 10.000 #> 2: 18.000 19.000 #> 3: 24.400 27.100 #> 4: 29.520 34.390 #> 5: 33.616 40.951 的并集独占。有两种方法可以做到这一点。

手动

这将确保i1 | i2上的yz永远不会存在。

i1

仅此一项更改就会给我们带来所需的错误。

使用助手

我们可以创建一个功能相同但可重用的助手。

interface i1 {
  x: number;
  y?: never;
  z?: never;
}

用法:

type DistributedKeyOf<T> =
T extends any
    ? keyof T
    : never;


type CreateExclusiveUnion<T, U = T> =
T extends any
    ? T & Partial<Record<Exclude<DistributedKeyOf<U>, keyof T>, never>>
    : never;

type ExclusiveUnion<T> = CreateExclusiveUnion<T>;