TypeScript如何将源对象指定属性复制到已有目标对象并保障编译安全
类型安全的对象指定属性复制方案
你需要的编译时属性校验完全可以通过TypeScript泛型约束实现,不需要特殊的参数传递形式,传入字符串数组时TS会自动校验属性合法性,写错属性名、类型不匹配都会在编译阶段直接抛出错误。
函数实现
/** * 从源对象复制指定属性到目标对象,直接修改目标对象 * @param source 源对象 * @param target 目标对象 * @param keys 要复制的属性名数组,仅支持传入源对象和目标对象共有的属性 */ function copyPropertyValues<S extends object, T extends object, K extends keyof S & keyof T>( source: S, target: T, keys: K[] ): void { keys.forEach(key => { target[key] = source[key] as T[K]; }); }
使用示例
const obj1 = { a: 'A', b: 'B', c: 'C', d: 'D' }; const obj2 = { b: 'B2', c: 'C2', d: 'D2', e: 'E2' }; // 仅复制b、d两个属性,IDE会自动补全可选属性,写错属性名TS会直接报错 copyPropertyValues(obj2, obj1, ['b', 'd']); // 执行后obj1的值为:{ a: 'A', b: 'B2', c: 'C', d: 'D2' } console.log(obj1);
如果不想直接写字符串字面量,也可以提前定义属性常量,效果完全一致:
const keysToCopy = ['b', 'd'] as const satisfies (keyof typeof obj2)[]; copyPropertyValues(obj2, obj1, keysToCopy);
需求匹配说明
- 仅复制指定属性:只会操作传入的
keys列表中的属性,不会修改其他属性 - 直接修改原对象:没有生成新对象,直接对传入的
target对象做修改 - 保留目标对象其余属性:未在
keys列表中的属性完全保持原值 - 编译时安全:
- 传入不存在的属性名(比如
['f']),TS会直接抛出类型错误 - 源对象和目标对象对应属性的类型不兼容时,TS也会提前报错
- IDE会自动提示可传入的属性名,不需要手动记忆属性名
- 传入不存在的属性名(比如
内容的提问来源于stack exchange,提问作者Arghya Chakrabarty
相关产品推荐
相关产品推荐

