as I understood, the method clone()
gives us the ability to copy object (no refernce) in Java. But I also read, that the copy is shallow. So what the point? Which a
Shallow copy is the default for Object. you can override clone to do a deep copy.
to clone in depth you have to implement Cloneable and override clone()
public class MyClass implements Cloneable {
private Object attr = new Object();
@Override
public Object clone() throws CloneNotSupportedException {
MyClass clone = (MyClass)super.clone();
clone.attr = new Object();
return clone;
}
@Override
public String toString() {
return super.toString()+", attr=" + attr;
}
public static void main(String[] args) throws Exception {
MyClass x = new MyClass();
System.out.println("X="+x);
MyClass y = (MyClass)x.clone();
System.out.println("Y="+y);
}
}
A simple assignment will simply create an Alias for the object. With clone(), each attribute member will also be initialized in the clone Object. However, if the Attribute members are themselves have more objects contained within them, those will not not be copied.
An assignment copies the reference of an instance to a variable. A clone operation will clone the instance (and assign a reference to the clone).
With assignment, you'll end up with multiple variables pointing to one object, with cloning you'll have multiple variables that hold references of multiple objects.
SomeCloneable a = new SomeCloneable();
SomeCloneable b = a; // a and b point to the same object
/* versus */
SomeCloneable a = new SomeCloneable();
SomeCloneable b = a.clone(); // a and b point to the different objects
The difference is that you can modify the cloned object without modifying the original object.
Point p = new Point(1,2);
Point p2 = p.clone();
Point p3 = p;
p2.x = 5;
p3.y = 7;
The change on p3
does feed back to p
, while the change on p2
does not.
Let's see how the situation is after the individual statements (assuming 1
, 2
, 5
, 7
would be objects):
Point p = new Point(1,2);
.-----. .-----.
p -----> | x -+--> | 1 |
| | '-----'
| | .-----.
| y -+--> | 2 |
'-----' '-----'
Point p2 = p.clone();
.-----. .-----. .-----.
p -----> | x -+--> | 1 | <--+- x | <----- p2
| | '-----' | |
| | .-----. | |
| y -+--> | 2 | <--+- y |
'-----' '-----' '-----'
Point p3 = p;
.-----. .-----. .-----.
p -----> | x -+--> | 1 | <--+- x | <----- p2
| | '-----' | |
| | .-----. | |
p3 -----> | y -+--> | 2 | <--+- y |
'-----' '-----' '-----'
p2.x = 5;
.-----. .-----. .-----. .-----.
p -----> | x -+--> | 1 | | x -+--> | 5 |
| | '-----' | | '-----'
| | .-----. | |
p3 -----> | y -+--> | 2 | <--+- y | <----- p2
'-----' '-----' '-----'
p3.y = 7;
.-----. .-----. .-----. .-----.
p -----> | x -+--> | 1 | | x -+--> | 5 |
| | '-----' | | '-----'
| | .-----. | |
p3 -----> | y | | 2 | <--+- y | <----- p2
'--+--' '-----' '-----'
| .-----.
'---> | 7 |
'-----'