为何无法用变量x的键对变量y进行索引?
为什么不能用变量x的键对变量y进行索引?
先看你给出的代码和报错:
interface A { a: string; b: number; e: boolean; }; declare let x: A; declare let y: A; let t: keyof typeof x; for (t in x) { y[t] = x[t]; }
报错信息:Type 'string | number | boolean' is not assignable to type 'never'. Type 'string' is not assignable to type 'never'.(2322)
问题原因
TypeScript的类型检查器在for-in循环里没办法细化keyof A类型变量t的具体值。它只知道t是"a"、"b"或"e"中的某个键,但没法在每次循环迭代中跟踪t对应的具体属性类型。
当执行y[t] = x[t]时,TypeScript会把x[t]推断为string | number | boolean(也就是A所有属性类型的联合),而y[t]的类型被推断为never——因为TypeScript无法保证当前迭代中x[t]的类型和y[t]的类型完全匹配(比如t可能是"a"对应string,也可能是"b"对应number),所以判定类型不兼容,抛出错误。
解决方案
1. 类型断言
直接告诉TypeScript当前x[t]的类型和y[t]匹配:
interface A { a: string; b: number; e: boolean; }; declare let x: A; declare let y: A; let t: keyof typeof x; for (t in x) { y[t] = x[t] as typeof y[typeof t]; }
2. 泛型函数封装
用泛型绑定键和对应值的类型,确保类型匹配:
interface A { a: string; b: number; e: boolean; }; declare let x: A; declare let y: A; function copyProp<K extends keyof A>(key: K) { y[key] = x[key]; } for (const t in x) { copyProp(t as keyof A); }
3. 对象展开/Object.assign(最简便)
如果只是要复制所有属性,没必要手动循环,直接用对象展开或Object.assign:
interface A { a: string; b: number; e: boolean; }; declare let x: A; declare let y: A; // 方式一:对象展开 y = {...x}; // 方式二:Object.assign Object.assign(y, x);
内容的提问来源于stack exchange,提问作者dlynch
相关产品推荐
相关产品推荐

