2010-12-08 10 views
1

Klonen Angenommen, ein Objekt mit diesen EigenschaftenObjekt durch Reflexion mit speziellen Einschränkungen

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; } 

i prop1 und prop2 mit dieser Methode kopieren:

public static void SetProperties(PropertyInfo[] fromFields, 
              object fromRecord, 
              object toRecord) 
    { 
     PropertyInfo fromField; 

     if (fromFields == null) 
     { 
      return; 
     } 

     foreach (PropertyInfo t in fromFields) 
     { 
      fromField = t; 

      fromField.SetValue(toRecord, 
           fromField.GetValue(fromRecord, null), 
           null); 
     } 
    } 

aber ich weiß nicht, wie jede Kopie von prop3, prop4 und prop5 zu einem anderen Objekt!

Edit: ich sollte nichtSerialize Objekt! Ich mache diese Arbeit, weil mein Objekt große Daten hat und mit diesem Trick kann ich einige Daten kopieren.

es ist lustig zu sagen, wenn ich Originalquelle dieses Problems sage! Ich verwende EF als ORM und verwende Datenobjekte in einem Silverlight Clients über WCF. Wenn ich List<Foo> in WCF sende, sendet es List<Foo> und seine Beziehungsdaten !! und Kunden starben!

+0

Ihr Punkt über die Verwendung von Serialisierung ist auf mich verloren; Wenn Sie ein großes Diagramm ("Big Data") klonen wollen, haben Sie 2 * ein großes Diagramm - die Serialisierung in der Mitte scheint irrelevant. –

+0

@Marc Gravell: Kopieren Sie einfach eine Eigenschaft mit EntityCollection <> über Reflektion. –

+0

rechts; Entweder möchten Sie einen tiefen Klon (in diesem Fall Serialize sollte funktionieren, und Sie werden doppelt so viele Daten haben), oder Sie wollen eine Kopie der Entitätssammlung (rufen Sie einfach 'SetValue' auf) - es ist immer noch nicht klar zu mir, wo das Problem liegt. –

Antwort

1

Was ich tun würde, ist die Objekte Serializable machen. Sie können dann das Objekt im Speicher serialisieren und es als neues geklontes Objekt deserialisieren.

Ich habe diese beiden Funktionen:

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); 
    } 

mit Ihrer Klasse wie dieses

[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; } 
} 

Sie jetzt die Klasse Speicher serialisiert werden kann und einen Klon von dem erstellen.

public MyClass Clone() 
{ 
    var myclass = new MyClass(); 
    /* Do Some init */ 

    var ms = ToMemoryStream(myclass); 

    var myNewObject = FromMemoryStream<MyClass>(ms); 
    return myNewObject; 
} 
+0

Beachten Sie, dass X, Y und Z in diesem Beispiel auch 'Serializable' sein sollten. – jvanrhyn

+0

Ich habe die Frage bearbeitet. –

1

Sie haben folgende Zeile

fromField.SetValue(toRecord, 
          fromField.GetValue(fromRecord, null), 
          null); 

Mit diesen Aussagen,

 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); 
     } 

Sie IList wahrscheinlich auf eine geeignete Schnittstelle ersetzen müssen ersetzen ICollection oder etwas anderes, das mit EntityCollection arbeiten Ich hatte nichts zu testen, also habe ich gerade dieses Beispiel gepostet.

Verwandte Themen