c# - objetos - ¿Cómo implementar el método Clonar y Copiar dentro de una Clase?
implements cloneable (6)
¿Quiere decir cómo implementar ICloneable.Clone () y hacer que devuelva el tipo de la clase en sí misma?
public class MyType : ICloneable
{
public MyType Clone() //called directly on MyType, returns MyType
{
return new MyType(/* class-dependant stuff goes here */);
}
object ICloneable.Clone() // called through ICloneable interface, returns object
{
return Clone();
}
}
Tengo una clase llamada Employee
with 3 property called ID
, Name
, Dept
Necesito implementar el método Copy
y Clone
? Cuando uso el método Copy
o Clone
, ¿debo evitar Casting? ¿cómo voy a hacer eso?
ejemplo: igual que DataTable
que tiene DataTable.Copy()
y DataTable.Clone()
.
¿Tiene que usar la interfaz ICloneable o es suficiente si solo tiene dos métodos llamados Clone
and Copy
definidos en una interfaz genérica?
public class YourClass : ICloneable<YourClass>
{
// Constructor logic should be here
public YourClass Copy() { return this; }
public YourClass Clone() { return new YourClass(ID, Name, Dept); }
}
interface IClonable<T>
{
T Copy();
T Clone();
}
¿O he entendido mal algo?
Lo que estoy tratando de decir es que no tienes que hacerlo más complejo de lo que es? Si necesita que sus objetos se ajusten a alguna clase de usted, puede escribirlo usted mismo si el que se especifica en el marco .Net es complejo para la situación. También debe definir la diferencia con Clone
y Copy
, es decir, ¿qué significan para usted? Sé que hay varios sitios que especifican que Clone
es una copia profunda y Copy
es una copia superficial.
A menudo veo constructores de copia sugeridos como una alternativa a un método de clonación, pero a excepción de las clases selladas, los comportamientos son muy diferentes. Si tengo un tipo Car, que simplemente admite propiedades VIN, BodyColor y BodyStyle, y un tipo derivado FancyCar, que también es compatible con InteriorFabric y SoundSystem, entonces el código que acepta un objeto de tipo Car y usa el constructor copia de coche para duplicarlo terminará arriba con un auto Si se pasa un FancyCar a dicho código, el "duplicado" resultante será un nuevo automóvil, que tiene un VIN, BodyColor y BodyStyle que coincide con el automóvil original, pero que no tendrá InteriorFabric o SoundSystem. Por el contrario, el código debía aceptar un automóvil y usar un método de clonación en él, pasar un FancyCar al código provocaría la producción de un FancyCar.
A menos que uno quiera usar Reflection, cualquier método de clonación debe incluir en su base una llamada a base.MemberwiseClone. Como MemberwiseClone no es un método virtual, sugeriría definir un método de clonación virtual protegido; es posible que también desee evitar que las clases secundarias llamen a MemberwiseClone definiendo una clase simulada de ámbito protegido con el mismo nombre (de modo que si una clase descendiente intenta llamar a base.MemberwiseClone, no se interpretaría como una referencia sin sentido al clase ficticia).
Aquí un ejemplo:
namespace XXX
{
[Serializable]
public class ItemChecklist : ICloneable
{
// [...here properties, attributes, etc....]
object ICloneable.Clone()
{
return this.Clone();
}
public ItemChecklist Clone()
{
return (ItemChecklist)this.MemberwiseClone();
}
}
}
es decir, si usa esta función, tendrá en "itemAdd" una copia completa del objeto "itemTemp" con todos sus valores.
ItemChecklist itemAdd = itemTemp.Clone();
Compruebe este objeto Clonación con IL en C # http://whizzodev.blogspot.com/2008/03/object-cloning-using-il-in-c.html
Debe implementar la interfaz IClonable y proporcionar implementación para el método de clonación. No implemente esto si quiere evitar el lanzamiento.
Un método simple de clonación profunda podría ser serializar el objeto en la memoria y luego deserializarlo. Todos los tipos de datos personalizados utilizados en su clase deben ser serializables mediante el atributo [Serializable]. Para clonar puedes usar algo como
public MyClass Clone()
{
MemoryStream ms = new MemoryStream();
BinaryFormatter bf = new BinaryFormatter();
bf.Serialize(ms, this);
ms.Position = 0;
object obj = bf.Deserialize(ms);
ms.Close();
return obj as MyClass;
}
Si su clase solo tiene tipos de valores , puede usar un constructor de copias o simplemente asignar los valores a un nuevo objeto en el método Clonar.