如何在C#中仅复制对象匹配字段值且不修改不匹配字段?
问题描述
我定义了两个类:
Car { string Color; } ModifiedCar{ string Color; int Price; }
并创建了两个对象:
var obj1 = new Car{ Color = "red"; } var obj2 = new ModifiedCar{ Color = "green"; Price = 330442; }
我希望把obj1里的匹配字段值(也就是Color字段)复制到obj2中,同时保留Price字段的值不变,最终得到的obj2应该是:
obj2 ={ Color = "red"; Price = 330442; }
手动逐个赋值(比如obj2.Color = obj1.Color)在字段多的时候太麻烦,想知道有没有.NET内置的函数或者技巧,不用手动写每个字段的赋值就能完成这种匹配字段的复制?
可行方案
1. 用反射实现批量复制(.NET内置)
反射是.NET自带的功能,可以遍历类的成员,自动复制名称和类型都匹配的字段/属性。写个通用方法就能复用:
using System.Reflection; using System.Linq; public static void CopyMatchingMembers<TFrom, TTo>(TFrom source, TTo target) { // 获取源类型的所有公共实例字段 var sourceFields = typeof(TFrom).GetFields(BindingFlags.Public | BindingFlags.Instance); // 获取目标类型的所有公共实例字段 var targetFields = typeof(TTo).GetFields(BindingFlags.Public | BindingFlags.Instance); foreach (var sourceField in sourceFields) { // 找目标类型里同名称同类型的可写字段 var targetField = targetFields.FirstOrDefault(f => f.Name == sourceField.Name && f.FieldType == sourceField.FieldType); if (targetField != null) { targetField.SetValue(target, sourceField.GetValue(source)); } } } // 调用方法复制字段 CopyMatchingMembers(obj1, obj2);
如果你的类用的是属性(Property)而不是字段(Field),把代码里的GetFields换成GetProperties,并检查CanWrite属性确保目标属性可写。
2. 用记录类型的With表达式(.NET 6+适用)
如果把类改成记录类型,可以用With表达式快速生成新对象(注意这是创建新对象,不是修改原obj2):
// 定义记录类型 public record Car(string Color); public record ModifiedCar(string Color, int Price); // 生成新的ModifiedCar对象,保留原Price,替换Color为obj1的Color var updatedObj2 = obj2 with { Color = obj1.Color };
这种写法非常简洁,但只适用于记录类型,且是生成新对象而非修改原实例。
3. 第三方库辅助(比如AutoMapper)
如果项目允许引入第三方包,AutoMapper可以自动处理匹配字段的映射,配置一次后就能复用:
// 安装AutoMapper NuGet包后,初始化映射配置(全局做一次就行) var mapperConfig = new MapperConfiguration(cfg => { cfg.CreateMap<Car, ModifiedCar>(); }); var mapper = mapperConfig.CreateMapper(); // 直接把obj1的匹配字段映射到obj2上,会更新obj2的对应字段 mapper.Map(obj1, obj2);
不过这不属于.NET内置功能,需要额外安装依赖。
内容的提问来源于stack exchange,提问作者Imtiaz Mehedi
相关产品推荐
相关产品推荐

