TypeScript泛型函数filterByArrayConditions编写报错,求正确实现方法
解决TypeScript过滤函数的索引类型错误
错误原因
- 原函数的泛型
T和K无类型约束,TypeScript无法确定item(类型T)支持索引访问,因此抛出索引类型错误 - 使用
Array<K>作为条件参数类型不合理,实际需要的是键值对形式的条件对象而非数组,for...in遍历数组得到的是索引字符串,和对象属性匹配逻辑冲突
修正方案
方案1:约束条件为目标对象的子集(最常用)
export function filterByArrayConditions<T extends Record<string, unknown>>( data: T[], conditions: Partial<T> ): T[] { return data.filter(item => { for (const key in conditions) { // 跳过原型链上的属性,避免误判 if (!conditions.hasOwnProperty(key)) continue; // 仅当条件值不为undefined时进行匹配,避免过滤属性本身为undefined的项 if (conditions[key] !== undefined && item[key] !== conditions[key]) { return false; } } return true; }); }
T extends Record<string, unknown>:强制T为带有字符串索引的对象类型,确保item[key]的访问合法Partial<T>:限定条件对象是T的部分属性子集,类型检查更严格
方案2:支持更多键类型(字符串/数字/符号)
如果需要匹配数字键或符号键,可将索引约束改为PropertyKey(TypeScript内置类型,包含string | number | symbol):
export function filterByArrayConditions<T extends Record<PropertyKey, unknown>>( data: T[], conditions: Partial<T> ): T[] { return data.filter(item => { for (const key in conditions) { if (!conditions.hasOwnProperty(key)) continue; if (conditions[key] !== undefined && item[key] !== conditions[key]) { return false; } } return true; }); }
使用示例
interface User { id: number; name: string; age?: number; } const users: User[] = [ { id: 1, name: 'Alice', age: 25 }, { id: 2, name: 'Bob' }, { id: 3, name: 'Alice', age: 30 } ]; // 过滤name为Alice的用户 const aliceUsers = filterByArrayConditions(users, { name: 'Alice' }); // 过滤id为2的用户 const user2 = filterByArrayConditions(users, { id: 2 });
内容的提问来源于stack exchange,提问作者ko1p
相关产品推荐
相关产品推荐

