Java's default cloning mechanism is discouraged to use, not only because
it's difficult to implement a correct one that complies with the
contract, but also one must try/catch the messy CloneNotSupported
exception that bloats up the codes.
Because of this, on the internet,
there are many serializer-based auto cloning libraries. However, first,
they use serialization, so dont expect those to be fast, second just
for a simple cloning, you must include a huge library -- not quite
economical.
Finally one can choose to manually create a clone method
which assigns every field with the values from the source object. This
is feasible, but very tedious and error prone, especially when someone
else modifies the class and fails to change the clone method accordingly.
Now,
this provides an excellent opportunity for lombok to shine. With
lombok, i think it's quite natural to add a @CopyCtor annotation which
generates codes just like the manual cloning while automatically updates
when the fields of the class change.
Even better, when no new object
is wanted during copying, a @CopySetter annotation would be very
useful. It's basically the same of CopyCtor, only that it's not a
constructor.
Example:
@CopyCtor
public class Foo {
private int id;
private String name;
@DeepCopy private ArrayList relationaships;
@SwallowCopy private ArrayList managers;
private final int rank=2;
public Foo() {}
}translates to:
public class Foo {
private int id;
private String name;
private ArrayList relationships;
private ArrayList managers;
private final int rank=2;
public Foo() {}
public Foo(Foo another) {
id = another.id;
name = another.name;
relationships = Arrays.copyOf( another.relationships );
managers = another.managers;
}
}if CopyCtor and CopySetter are used together, then above codes becomes:
public class Foo {
private int id;
private String name;
private ArrayList relationships;
private ArrayList managers;
private final int rank=2;
public Foo() {}
public Foo(Foo another) {
set(another);
}
public void set(Foo another) {
id = another.id;
name = another.name;
relationships = Arrays.copyOf( another.relationships );
managers = another.managers;
}
}