1

There seems to be a consensus that Java's clone is broken to the extent that it should never be used if at all possible.

I have a situation where it seems like clone is the right tool, but I'm wondering if there's another way:

I have a variety of objects stored in a mongo database. They are saved and loaded using Morphia, which automagically returns objects with their correct class and properties.

In some cases, what is stored in the database is a "prototype" for an object that I want to create copies of. It comes out of morphia with the correct class and default values, and I want to be able to make a copy that preserves the class and default values. E.g.:

achievementPrototype = morphia.get(id); playerAchievements.add(achievementPrototype.clone());

Where achievementPrototype is of a class that's a concrete implementation of an AbstractAchievement. It seems like clone does what I want. I'm aware that if achievements have objects as properties I'll have to implement their cloning, but I'm okay with that.

Should I use clone()? If not, what should I use?

Luiggi Mendoza
  • 85,076
  • 16
  • 154
  • 332
justkevin
  • 3,089
  • 3
  • 28
  • 33

2 Answers2

1

It not that its broken, but it doesn't work the way most want it to without modifying it. Your objects will have to implement Cloneable and also override the clone() method in order to make it public. There are a some alternatives to this which I personally prefer.

BeanUtils:
BeanUtils.cloneBean(objectToClone) will create a shallow clone similar to what would be created with Object.clone().

SerializationUtils:
SerializationUtils.clone(objectToClone) will create a deep clone, which you might be looking for, but all objects must implement Serializable.

Joe
  • 661
  • 2
  • 8
  • 15
0

If you just want to create new objects that can be subsequently saved and get new IDs and thus are copies in the database, just clear the ID field and when morphia goes to save those objects again, it'll think they're new because they have no IDs and will generate new IDs for them.

evanchooly
  • 6,102
  • 1
  • 16
  • 23
  • Thanks, but the application needs to be able to create separate instances that are copies/clones of a prototype without the overhead of saving/loading each one from the db. – justkevin Oct 22 '13 at 21:24
  • Oh, so you need them irrespective of mongo and persistence. I'd still avoid clone() and just write a constructor that takes an instance of the class and copy the values over. – evanchooly Oct 22 '13 at 21:26