如何在TypeScript中递归且条件性提取嵌套类型的键?
递归提取嵌套数据中
hasPets为true的对象键 我们需要定义一个TypeScript类型,从嵌套数据结构中提取所有满足hasPets属性值恒为true的对象对应的父键。例如给定以下嵌套数据类型:
type NestedData = { first: { name: string; age: number; hasPets: true; children: { second: { name: string; age: number; hasPets: false; children: { third: { name: string; age: number; hasPets: true; }; }; }; }; }; };
期望KeysWithPets<NestedData>的结果为'first' | 'third'。
原有类型的问题分析
你尝试的递归类型仅能提取第一层符合条件的键,原因在于当某个键对应的值本身是hasPets: true的对象时,类型只返回了当前键,没有递归处理该对象内部的嵌套结构。例如处理first键时,仅返回了'first',而没有继续遍历其children属性去提取深层的'third'键。
修正后的类型实现
修正后的类型需要同时处理当前层符合条件的键,以及递归遍历当前值内部的所有嵌套结构,提取深层符合条件的键:
type KeysWithPets<T> = { [K in keyof T]: // 若当前键对应的值是hasPets为true的对象,保留该键 (T[K] extends { hasPets: true } ? K : never) // 递归处理当前值的嵌套结构,提取深层符合条件的键 | KeysWithPets<T[K]> }[keyof T] extends infer U ? U extends never ? never : U : never;
工作原理
- 遍历输入类型
T的每个键K:- 首先判断
T[K]是否是包含hasPets: true的对象,若是则将K加入结果; - 同时递归调用
KeysWithPets<T[K]>,提取该值内部嵌套结构中符合条件的键;
- 首先判断
- 通过
[keyof T]将所有键对应的结果合并为联合类型; - 最后通过条件类型过滤掉
never类型,确保结果仅包含有效键。
将该类型应用到NestedData上,KeysWithPets<NestedData>会正确返回'first' | 'third',符合预期。
内容的提问来源于stack exchange,提问作者IgStefano
相关产品推荐
相关产品推荐

