Pregunta ¿Cuál es la diferencia entre una copia profunda y una copia superficial?


¿Cuál es la diferencia entre una copia profunda y una copia superficial?


755
2017-10-08 20:22


origen


Respuestas:


Las copias superficiales duplican lo menos posible. Una copia superficial de una colección es una copia de la estructura de la colección, no de los elementos. Con una copia superficial, dos colecciones ahora comparten los elementos individuales.

Las copias profundas duplican todo. Una copia profunda de una colección es dos colecciones con todos los elementos de la colección original duplicados.


592
2017-10-08 20:29



Amplitud frente a profundidad; piense en términos de un árbol de referencias con su objeto como nodo raíz.

Superficial:

Before Copy Shallow Copying Shallow Done

Las variables A y B se refieren a diferentes áreas de la memoria, cuando B se asigna a A, las dos variables se refieren a la misma área de memoria. Las modificaciones posteriores a los contenidos de cualquiera de ellas se reflejan instantáneamente en los contenidos de otros, a medida que comparten contenidos.

Profundo:

Before Copy Deep Copying Deep Done

Las variables A y B se refieren a diferentes áreas de la memoria, cuando B se asigna a A, los valores en el área de memoria a la que apunta A se copian en el área de memoria a la que B apunta. Las modificaciones posteriores a los contenidos de cualquiera permanecen únicas para A o B; los contenidos no son compartidos


711
2017-10-08 20:39



En resumen, depende de qué puntos a qué. En una copia superficial, el objeto B apunta a la ubicación del objeto A en la memoria. En una copia profunda, todas las cosas en la ubicación de la memoria del objeto A se copian en la ubicación de memoria del objeto B.

Este artículo wiki tiene un gran diagrama.

http://en.wikipedia.org/wiki/Object_copy


135
2017-10-08 20:24



Especialmente para desarrolladores de iOS: 

Si B es un copia superficial de A, entonces para datos primitivos es como B = [A assign]; y para los objetos es como B = [A retain];

B y A señalan la misma ubicación de memoria

Si B es un copia profunda de A, entonces es como B = [A copy];

B y A señalan diferentes ubicaciones de memoria

La dirección de memoria B es igual a la de A

B tiene el mismo contenido que el de A


68
2018-01-23 11:43



Copia superficial: copia los valores de miembros de un objeto a otro.

Copia profunda: copia los valores de los miembros de un objeto a otro.
Todos los objetos de puntero se duplican y se copian en profundidad.

Ejemplo:

class String
{
     int   size;
     char* data;
};

String  s1("Ace");   // s1.size = 3 s1.data=0x0000F000

String  s2 = shallowCopy(s1);
 // s2.size =3 s2.data = 0X0000F000
String  s3 = deepCopy(s1);
 // s3.size =3 s3.data = 0x0000F00F
 //                      (With Ace copied to this location.)

54
2017-10-08 20:25



Trata de considerar la siguiente imagen

enter image description here

Por ejemplo Object.MemberwiseClone crea un superficial dupdo enlazar

y usando ICloneable interfaz que puedes obtener profundo copiar como se describe aquí


51
2018-06-15 08:42



No he visto una respuesta corta y fácil de entender aquí, así que lo intentaré.

Con una copia superficial, cualquier objeto apuntado por la fuente también apunta al destino (para que no se copien los objetos referenciados).

Con una copia profunda, cualquier objeto apuntado por la fuente se copia y la copia apunta al destino (por lo que ahora habrá 2 de cada objeto referenciado). Esto vuelve a mostrar el árbol de objetos.


40
2017-10-08 20:36



{Imagina dos objetos: A y B del mismo tipo _t (con respecto a C ++) y estás pensando en copiar superficialmente a A a B}

Copia superficial: Simplemente hace una copia de la referencia a A en B. Piense en ello como una copia de la Dirección de A. Por lo tanto, las direcciones de A y B serán las mismas, es decir, señalarán la misma ubicación de memoria, es decir, los contenidos de datos.

Copia profunda Simplemente hace una copia de todos los miembros de A, asigna una memoria en una ubicación diferente para B y luego asigna los miembros copiados a B para lograr una copia en profundidad. De esta forma, si A pasa a ser no existente, B sigue siendo válido en la memoria. El término correcto para usar sería la clonación, donde sabe que ambos son totalmente iguales, pero diferentes (es decir, almacenados como dos entidades diferentes en el espacio de la memoria). También puede proporcionar su contenedor clónico donde puede decidir a través de la lista de inclusión / exclusión qué propiedades seleccionar durante la copia profunda. Esta es una práctica bastante común cuando creas API.

Puede elegir hacer una copia superficial SÓLO SI usted entiende lo que está en juego. Cuando tiene que lidiar con una cantidad enorme de punteros en C ++ o C, hacer una copia superficial de un objeto es DE VERDAD una mala idea.

EJEMPLO_DE_DE COPIA_ Un ejemplo es que cuando intenta hacer procesamiento de imágenes y reconocimiento de objetos, necesita enmascarar el "Movimiento irrelevante y repetitivo" fuera de sus áreas de procesamiento. Si está utilizando punteros de imagen, es posible que tenga la especificación para guardar esas imágenes de máscara. AHORA ... si hace una copia superficial de la imagen, cuando las referencias del puntero se eliminan de la pila, pierde la referencia y su copia, es decir, habrá un error en el tiempo de ejecución de violación de acceso en algún momento. En este caso, lo que necesita es una copia profunda de su imagen CLONANDO. De esta forma, puedes recuperar las máscaras en caso de que las necesites en el futuro.

EXAMPLE_OF_SHALLOW_COPY No estoy muy bien informado en comparación con los usuarios de StackOverflow, así que puede eliminar esta parte y poner un buen ejemplo si puede aclarar. Pero realmente creo que no es una buena idea hacer una copia superficial si sabes que tu programa se ejecutará por un período infinito de tiempo, es decir, una operación continua de "push-pop" sobre la pila con llamadas a funciones. Si estás demostrando algo a un aficionado o una persona novata (por ejemplo, material tutorial de C / C ++), entonces probablemente esté bien. Pero si está ejecutando una aplicación como un sistema de vigilancia y detección, o Sonar Tracking System, no se supone que debe mantener la poca profundidad de sus objetos porque tarde o temprano matará su programa.


32
2018-01-31 23:39



Solo por el simple hecho de entender, podrías seguir este artículo: https://www.cs.utexas.edu/~scottm/cs307/handouts/deepCopying.htm


Copia superficial:

Shallow Copy 


Copia profunda:

Deep Copy


28
2018-03-19 06:15