À propos de Java clonable
Je cherchais des tutos expliquant à propos de Java Cloneable
, mais n'a pas obtenu de bons liens, et de Débordement de Pile est de plus en plus évident le choix de toute façon.
Je voudrais savoir les suivantes:
Cloneable
signifie que nous pouvons avoir un clone ou une copie d'objets, par
la mise en œuvre de laCloneable
interface. Quels sont les avantages et les
les inconvénients de le faire?- Comment le récursive clonage se produire si l'objet est un
objet composite?
- Les avantages et les inconvénients par rapport à quoi?
- J'ai lu que pour signifier l'avantage de la classe Clonable vs pas. Vous ne savez pas faire autre chose qui pourrait être interprété :S
Vous devez vous connecter pour publier un commentaire.
La première chose que vous devez savoir à propos de
Cloneable
est - ne l'utilisez pas.Il est très difficile de mettre en œuvre le clonage avec
Cloneable
droit, et l'effort en vaut pas la peine.Plutôt que d'utiliser les autres options, comme apache commons
SerializationUtils
(deep-clone) ouBeanUtils
(shallow-clone), ou tout simplement utiliser un constructeur par copie.Voir ici pour le point de vue de Josh Bloch à propos du clonage avec
Cloneable
, ce qui explique les nombreux inconvénients de l'approche. (Joshua Bloch était un employé de Sun, et conduit au développement de nombreuses fonctionnalités Java.)Clonable lui-même n'est malheureusement qu'un marqueur de l'interface, c'est: il ne définit pas la méthode clone ().
Ce qui est fait, est de modifier le comportement de l'Objet protégé.méthode clone (), qui va lancer une CloneNotSupportedException pour les classes qui n'implémentent pas Clonable, et d'effectuer un membre de la sage-copie pour les classes qui ne.
Même si c'est le comportement que vous cherchez, vous aurez toujours besoin pour mettre en œuvre votre propre méthode clone() dans le but de le rendre public.
Lors de la mise en œuvre de votre propre clone(), l'idée est de commencer avec l'objet créer par super.clone(), qui est garanti pour être de la classe correcte, puis effectuez l'une population supplémentaire de champs dans le cas d'une copie n'est pas ce que vous voulez. Appel d'un constructeur de clone() serait problématique car cela casserait l'héritage dans le cas d'une sous-classe veut ajouter ses propres clonable logique; si c'était pour appeler super.clone (), on pourrait obtenir un objet de la mauvaise classe dans ce cas.
Cette approche ignore tout de la logique qui peuvent être définis dans votre constructeurs, ce qui pourrait être problématique.
Un autre problème est que toutes les sous-classes qui oubliez pas de remplacer clone() héritera automatiquement la valeur par défaut copie superficielle, qui n'est probablement pas ce que vous voulez dans le cas d'mutable état (qui seront désormais partagées entre la source et la copie).
La plupart des développeurs n'utilisent pas Clonable pour ces raisons, et tout simplement de mettre en œuvre un constructeur de copie à la place.
Pour plus d'informations et les pièges potentiels de Clonable, je recommande fortement le livre Efficace Java par Joshua Bloch
Ainsi, l'utilisation de Clonable judicieusement. Il ne vous donne pas suffisamment d'avantages en comparaison avec l'effort que vous devrez appliquer pour tout faire correctement.
Le clonage est un paradigme de programmation. Le fait que Java peut avoir mis en œuvre mal dans beaucoup de façons de ne pas du tout diminuer le besoin de clonage. Et, il est facile à mettre en œuvre le clonage qui fonctionnera, toutefois, vous voulez que cela fonctionne, peu profond, profond, mixte, que ce soit. Vous pouvez même utiliser le nom de clone de la fonction et de ne pas mettre en œuvre Clonable si vous le souhaitez.
Supposons que j'ai des classes A, B, et C, où B et C sont des dérivés de A. Si j'ai une liste d'objets de type A comme ceci:
Maintenant, cette liste peut contenir des objets de type A, B ou C. Vous ne savez pas quel type les objets. Donc, vous ne pouvez pas copier la liste comme ceci:
Si l'objet est en fait de type B ou C, vous n'aurez pas le droit de copie. Et, si l'Un est abstrait? Maintenant, certaines personnes ont suggéré ceci:
C'est une très, très mauvaise idée. Si vous ajoutez un nouveau type dérivé? Que faire si B ou C sont dans un autre paquet, et vous n'avez pas accès à cette classe?
Ce que vous voulez faire est ceci:
Beaucoup de gens ont indiqué pourquoi la base Java mise en œuvre de clone est problématique. Mais, il est facilement surmonter cette façon:
Dans la classe A:
De la classe B:
Dans la classe C:
Je ne suis pas la mise en œuvre de Clonable, juste en utilisant le même nom de fonction. Si vous n'aimez pas que, nom de quelque chose d'autre.
Un) Il n'y a pas beaucoup d'avantages de clone sur un constructeur de copie. Probablement le plus grand est la possibilité de créer un nouvel objet du même type dynamique (en supposant que le type déclaré est clonable et a un public méthode clone).
B) La valeur par défaut clone crée une copie superficielle, et il restera une copie à moins que votre clone de mise en œuvre de changements. Cela peut être difficile, surtout si votre classe a final champs
Bozho est droit, le clone peut être difficile d'obtenir le droit. Un constructeur de copie/d'usine de servir à la plupart des besoins.
Quels sont les inconvénients de Clonable?
Le clonage est très dangereux si l'objet dont vous êtes la copie de la composition.Vous devez penser au-dessous de leurs effets secondaires possibles, dans ce cas, parce que clone crée la copie superficielle:
Disons que vous avez un objet à manipuler db liés à la manipulation. Dire que l'objet a
Connection
objet que celui de la propriété.Ainsi, lorsque quelqu'un crée clone de
originalObject
, L'objet créé, disons,cloneObject
.Ici le
originalObject
etcloneObject
tenir la même référence pourConnection
objet.Disons
originalObject
ferme laConnection
objet, de sorte que maintenant lecloneObject
ne fonctionnera pas car leconnection
objet a été partagé entre eux et il était actaually fermé par leoriginalObject
.Problème similaire peut se produire si, disons que vous voulez cloner un objet qui a IOStream comme une propriété.
Comment le récursive clonage se produire si l'objet est un objet composite?
Clonable effectue la copie superficielle. Le sens est que les données de l'objet original et le clone de l'objet point à la même référence/mémoire.
contraire dans le cas de la copie en profondeur, les données de la mémoire de l'objet original est copié dans la mémoire de cloner un objet.
Cloneable
n'a pas d'effectuer une copie,Object.clone
n'. "Les données de la mémoire de l'objet original est copié dans la mémoire de cloner un objet" est précisément ce queObject.clone
n'. Vous avez besoin de parler à propos de la mémoire des objets référencés pour décrire la profondeur de la copie.