You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何实现递归匹配类型键的PickMatchedKeys泛型类型?

实现递归的PickMatchedKeys<T, U>类型

这个递归筛选类型的需求挺实用的,我来给你实现一个符合预期的PickMatchedKeys<T, U>,同时一步步拆解逻辑:

完整实现代码

type PickMatchedKeys<T, U> = {
  // 第一步:筛选出同时存在于T和U中的键
  [K in keyof T as K extends keyof U ? K : never]: 
    // 第二步:递归处理嵌套对象
    T[K] extends object 
      ? U[K] extends object 
        ? PickMatchedKeys<T[K], U[K]> 
        : T[K]
      : T[K]
};

逻辑拆解

  1. 键的筛选(键重映射)
    这里用到了TypeScript的键重映射(Key Remapping)特性,通过K in keyof T as K extends keyof U ? K : never,我们只保留那些同时存在于T和U中的键——如果K是U的键就保留,否则就用never剔除这个键。

  2. 递归处理嵌套对象
    对于每个保留下来的键对应的类型:

    • 先判断T[K]是否为对象类型(如果你的场景只需要处理普通键值对对象,可以把object换成Record<string, any>来排除数组、函数等特殊对象)
    • 如果T[K]是对象,再检查U[K]是否也是对象——只有两者都是对象时,才递归调用PickMatchedKeys来处理嵌套的子结构
    • 如果其中一方不是对象,就直接保留T[K]的原始类型

验证你的示例

用你给出的测试类型验证一下:

type TargetType = {a: true, b: {c: true, d: true}};
type InputType = {a: string, b: { c: boolean, d: number, e: string }, f: number};

type Result = PickMatchedKeys<InputType, TargetType>;
// Result的最终类型为:{a: string, b: { c: boolean, d: number }},完全符合预期

补充说明

如果你的需求里需要处理数组或者其他复杂对象,可以调整对象判断的逻辑。比如要支持数组的话,可以把对象判断改成T[K] extends object | any[],不过根据你给出的示例,当前的实现已经完全满足需求了。

内容的提问来源于stack exchange,提问作者CRice

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.26 09:14:02