typescript - 如何在元组类型中表示所有可能的对象路径
问题描述
给定一个 object type SomeRecord = {a: {a1: 'a1', a2: 'a2'}, b: {b1: 'b1'}}
,我想要一个Path<T extends Record<string, any>>
将所有可能的记录路径表示为元组的类型:
// Path<SomeRecord> will be a union of:
['a']
['a', 'a1']
['a', 'a2']
['b']
['b', 'b1']
// And nothing else
我阅读了大量关于路径是函数参数的建议。这对我不起作用,因为我只需要元组。
解决方案
在我们开始之前,并不是说生成所有可能路径的联合可能很昂贵。在编译时间方面。此外,以下解决方案使用递归条件类型,它们有自己的性能问题,不鼓励使用。
最优雅的解决方案是使用 4.0(尚未发布)中的新 TS 功能,该功能允许在其他元组中传播元组,如此处所述。有了这个和递归条件类型,我们可以创建所有可能的元组路径:
type SomeRecord = { a: { a1: 'a1', a2: 'a2' }, b: { b1: 'b1', b2: { b21: string, b22: string, } } }
type Paths<T, K extends keyof T = keyof T> = K extends K ? [K, ...{
0: []
1: [] | Paths<T[K]>
}[T[K] extends string | number | boolean ? 0: 1]] : never;
type x = Paths<SomeRecord>
它的工作方式是,我们获取 中的每个键T
,并使用分布式条件类型来获取每个键K
并创建一个元组,其中K
是第一项,然后是:
[]
如果T[K]
没有我们感兴趣的其他键(即原语),则空元组 ( ) o- 或由
[]
(为了允许只是[K]
)与 . 类型的路径联合组成的元组T[K]
。
未标准化的结果将类似于['a', ...([] | ['a1'] | ['a2'])] | ['b', ...([] | ['b1'] | ['b2', ...([] | ['b21'] | ['b22'] ])]
. 幸运的是,编译器会将这种怪物标准化为["a"] | ["a", "a1"] | ["a", "a2"] | ["b"] | ["b", "b1"] | ["b", "b2"] | ["b", "b2", "b21"] | ["b", "b2", "b22"]
推荐阅读
- batch-file - 批量修改代理设置不起作用
- asp.net - asp引导选择不起作用
- c# - UWP AppServiceConnection - SendResponseAsync 返回 AppServiceResponseStatus.Failure
- c++ - 从部分专用的模板方法调用模板非静态方法
- python - 使用 int8 列检查 pandas 数据框中的 NaN 值
- html - 范围滑块拇指未在 IE 上显示
- python - python anaconda Py_Initialize:无法初始化 sys 标准流 LookupError:未知编码:65001
- java - java.util.zip“找不到文件”错误
- c# - .net Timer 事件处理程序能否修改非静态变量
- acumatica - PageTitle.ascx.cs 页面中的“未设置对象引用”错误