如何实现类型函数FilterFs以过滤对象类型中的F1、F2泛型类型
如何实现类型函数FilterFs以过滤对象类型中的F1、F2泛型类型
嘿,我来帮你搞定这个TypeScript类型过滤的问题!你想要的FilterFs类型函数核心就是遍历对象的每个属性,然后从属性的联合类型里剔除掉F1<any>、F2<any[], any>这些泛型类型,同时还要保留原属性的可选性、null这些其他类型对吧?咱们一步步来实现:
首先,先写一个处理单个属性类型的辅助工具——专门用来剔除F1、F2类型:
// 辅助类型:剔除单个类型中的F1、F2实例 type ExcludeFs<T> = T extends F1<any> | F2<any[], any> ? never : T;
这个逻辑很直白:用TypeScript的条件类型检查,如果当前类型T是F1或者F2的任意实例,就把它转换成never(也就是直接剔除),否则保留原类型。这样单个属性的过滤逻辑就搞定了。
接下来是核心的FilterFs类型,我们需要遍历原对象的所有属性,对每个属性应用上面的过滤逻辑,同时还要保留原属性的可选修饰符(比如原对象里的d?):
// 核心类型函数:过滤对象中所有属性的F1、F2类型 type FilterFs<T extends object> = { [K in keyof T]: ExcludeFs<T[K]>; };
这里用了TypeScript的映射类型[K in keyof T],它会自动遍历原对象的每一个键,并且保留原属性的可选性、readonly这些修饰符,完全不用额外处理,非常方便。
咱们拿你给出的例子来验证一下,先模拟基础类型和原对象类型:
// 模拟你提到的基础类型 type A = { aDetail: string }; type B = { bDetail: number }; type C = { cDetail: boolean }; type D = { dDetail: symbol }; type F1<T> = { f1Marker: T }; type F2<T1, T2> = { f2Marker: [T1, T2] }; // 原对象类型(换个名字避免和类型C重名) type OriginalC = { a: A | F1<any> | F2<any[], any>; b: B | F1<any> | F2<any[], any>; c: C | F1<any> | null; d?: D | F2<any[], any> | null; };
当你使用FilterFs<OriginalC>时,得到的类型就是:
{ a: A; b: B; c: C | null; d?: D | null; }
完全符合你想要的效果!如果遇到某个属性的类型全是F1/F2(比如x: F1<any>),过滤后会变成never,如果你需要这种情况返回默认值(比如undefined),只需要调整ExcludeFs的条件分支就行,比如改成:
type ExcludeFs<T> = T extends F1<any> | F2<any[], any> ? undefined : T;
这样就能根据你的具体需求灵活调整啦。
内容来源于stack exchange
相关产品推荐
相关产品推荐

