如何用TypeScript泛型约束T类型包含类型为T的K属性
解决TypeScript泛型约束:确保对象包含指定类型的自身属性
要实现你需要的泛型flatten函数,核心是通过泛型约束强制类型T必须包含一个名为K的属性,且该属性的类型就是T本身。以下是正确的实现方式:
正确的泛型函数定义
function flatten<T extends Record<K, T>, K extends keyof any>(tree: T, property: K): T { return tree[property]; }
约束解析
K extends keyof any:确保K是合法的对象键类型(字符串、数字或符号)。T extends Record<K, T>:约束类型T必须满足包含属性K,且该属性的类型为T。Record<K, T>表示一个键为K、值类型为T的对象结构,通过extends强制T必须匹配这个结构。
测试适配你的Tree类型
type Tree = { subTree: Tree; name: string; }; // 合法调用:"subTree"属性类型为Tree,符合约束 const tree: Tree = { name: "root", subTree: { name: "child", subTree: {} as Tree } }; const result = flatten(tree, "subTree"); // result类型为Tree // 非法调用:"name"属性类型为string,不符合约束,TypeScript会报错 flatten(tree, "name"); // 类型错误:类型'string'不能赋值给类型'Tree'
为什么你的原写法不生效
你之前的泛型定义<T, K>(tree: T, property: K): T没有任何约束:
- TypeScript无法确认
T包含K这个属性,会报“类型T上不存在属性K”的错误。 - 没有约束
T[K]的类型必须是T,无法保证返回值的类型正确性。
内容的提问来源于stack exchange,提问作者Konrad
相关产品推荐
相关产品推荐

