C# 通过具有特殊约束的反射克隆对象
假设一个对象具有此属性C# 通过具有特殊约束的反射克隆对象,c#,reflection,C#,Reflection,假设一个对象具有此属性 public int? Prop1 { get; set; } public string Prop2 { get; set; } public EntityCollection<X> Prop3 { get; set; } public EntityCollection<Y> Prop4 { get; set; } public EntityCollection<Z> Prop5 { get; set; } 但是我不知道如何将pro
public int? Prop1 { get; set; }
public string Prop2 { get; set; }
public EntityCollection<X> Prop3 { get; set; }
public EntityCollection<Y> Prop4 { get; set; }
public EntityCollection<Z> Prop5 { get; set; }
但是我不知道如何将prop3
、prop4
和prop5
复制到另一个对象上
编辑:
我应该不要序列化对象!我做这项工作是因为我的对象有大数据,通过这个技巧我可以复制一些数据
如果我说这个问题的根源,这很有趣!我使用EF
作为ORM
并通过WCF
在Silverlight
客户端中使用数据对象。当我在WCF
中发送List
时,它会发送List
及其关系数据!!客户死了 我要做的是使对象可序列化
。然后可以在内存中序列化该对象,并将其反序列化为新的克隆对象
我有两个功能:
public static MemoryStream ToMemoryStream(object entity)
{
MemoryStream ms = new MemoryStream();
BinaryFormatter formatter = new BinaryFormatter();
formatter.Serialize(ms, entity);
return ms;
}
public static T FromMemoryStream<T>(Stream stream)
{
BinaryFormatter formatter = new BinaryFormatter();
stream.Position = 0;
return (T)formatter.Deserialize(stream);
}
公共静态内存流到内存流(对象实体)
{
MemoryStream ms=新的MemoryStream();
BinaryFormatter formatter=新的BinaryFormatter();
序列化(ms、实体);
返回ms;
}
来自MemoryStream(流)的公共静态T
{
BinaryFormatter formatter=新的BinaryFormatter();
流位置=0;
返回(T)格式化程序。反序列化(流);
}
像这样和你的班级在一起
[Serializable]
public class MyClass
{
public int? Prop1 { get; set; }
public string Prop2 { get; set; }
public EntityCollection<X> Prop3 { get; set; }
public EntityCollection<Y> Prop4 { get; set; }
public EntityCollection<Z> Prop5 { get; set; }
}
[可序列化]
公共类MyClass
{
公共int?Prop1{get;set;}
公共字符串Prop2{get;set;}
公共EntityCollection Prop3{get;set;}
公共EntityCollection Prop4{get;set;}
公共EntityCollection Prop5{get;set;}
}
现在可以将该类序列化到内存中,并从中创建克隆
public MyClass Clone()
{
var myclass = new MyClass();
/* Do Some init */
var ms = ToMemoryStream(myclass);
var myNewObject = FromMemoryStream<MyClass>(ms);
return myNewObject;
}
publicMyClass克隆()
{
var myclass=新的myclass();
/*做一些初始化*/
var ms=多模流(myclass);
var myNewObject=FromMemoryStream(毫秒);
返回myNewObject;
}
您必须替换以下行
fromField.SetValue(toRecord,
fromField.GetValue(fromRecord, null),
null);
有了这些声明
if (typeof(IList).IsAssignableFrom(t.PropertyType))
{
IList fromList = fromField.GetValue(fromRecord, null);
IList toList = fromField.GetValue(toRecord, null);
foreach (var item in fromList)
toList.Add(item);
}
else
{
fromField.SetValue(toRecord,
fromField.GetValue(fromRecord, null),
null);
}
您必须将IList替换为某个合适的接口,可能是ICollection或其他可以与EntityCollection一起使用的接口,我没有任何东西要测试,所以我刚刚发布了这个示例。请记住,在这个示例中,X、Y和Z也应该是可序列化的。
。您关于不使用序列化的观点我不理解;如果你想克隆一个大的图(“大数据”),你将有2个大的图形——中间的序列化看起来是不真实的。@ Marc Gravell:只需通过ErrutsOrth.Trand复制一个带有EntyType类型的属性。因此,要么您想要一个深度克隆(在这种情况下序列化应该可以工作,并且您将拥有两倍的数据),要么您想要一个实体集合的副本(因此只需调用SetValue
)-我仍然不清楚问题出在哪里。如何使用EntityCollection类型反映属性
if (typeof(IList).IsAssignableFrom(t.PropertyType))
{
IList fromList = fromField.GetValue(fromRecord, null);
IList toList = fromField.GetValue(toRecord, null);
foreach (var item in fromList)
toList.Add(item);
}
else
{
fromField.SetValue(toRecord,
fromField.GetValue(fromRecord, null),
null);
}