Clone () vs Copiar constructor- que é recomendado em java [duplicado]
-
19-09-2019 - |
Pergunta
Esta questão já tem uma resposta aqui:
método clone vs construtor de cópia em java. que é uma solução correcta. onde usar cada caso?
Solução
Clone está quebrado, então não uso isso.
O método clone da classe Object é um método um tanto mágico que faz o que nenhum método Java pura poderia sempre fazer: Produz uma cópia idêntica de o seu objecto. Tem sido presente no superclasse objeto primordial uma vez que o dias Beta-lançamento do Java compilador*; e, como todos os antiga mágica, exige a adequada encantamento para impedir a passagem de inesperadamente backfiring
Prefere um método que copia o objecto
Foo copyFoo (Foo foo){
Foo f = new Foo();
//for all properties in FOo
f.set(foo.get());
return f;
}
Leia mais http://adtmag.com/articles/2000/01/18 /effective-javaeffective-cloning.aspx
Outras dicas
Tem em mente que clone()
não funciona fora da caixa. Você terá que implementar Cloneable
e substituir o método clone()
fazer em public
.
Existem algumas alternativas, que são preferíveis (já que o método clone()
tem muitos problemas de design, como afirmado em outras respostas), ea cópia-construtor exigiria um trabalho manual:
-
BeanUtils.cloneBean(original)
cria um clone superficial, como o criado porObject.clone()
. (Esta classe é de commons-beanutils ) -
SerializationUtils.clone(original)
cria um clone profundo. (Ou seja, todo o gráfico propriedades é clonado, não só o primeiro nível) (a partir de comuns-lang ), mas todas as classes devem implementarSerializable
-
Java Clonagem Biblioteca profunda ofertas profunda clonagem, sem a necessidade de implementar
Serializable
clone () foi projetado com vários erros (ver esta questão ) , por isso é melhor evitá-lo.
A partir Effective Java 2nd Edition , Item 11: Override clone criteriosamente
Tendo em conta todos os problemas associados com Cloneable, é seguro dizer que outras interfaces não deve estendê-lo, e que as classes projetado para herança (ponto 17) não deve implementá-lo. Por causa de suas muitas falhas, alguns programadores experientes simplesmente escolher para nunca mais substituir o método clone e nunca para invocá-lo, exceto, talvez, para copiar matrizes. Se você projetar uma classe para herança, estar ciente de que, se você optar por não fornecer um método clone bem-comportado protegido, será impossível para subclasses para implementar Cloneable.
Este livro também descreve as muitas vantagens copiar construtores têm sobre Cloneable / clone.
- Eles não dependem de um mecanismo extralingüística criação do objeto de risco propensas
- Eles não exigem a adesão inaplicável às convenções mal documentados
- Eles não entram em conflito com o uso adequado dos campos finais
- Eles não jogue exceções verificadas desnecessários
- Eles não necessitam de moldes.
Todas as coleções padrão têm construtores de cópia. Usá-los.
List<Double> original = // some list
List<Double> copy = new ArrayList<Double>(original);
Tenha em mente que o construtor de cópia limita o tipo de classe ao do construtor de cópia. Considere o exemplo:
// Need to clone person, which is type Person
Person clone = new Person(person);
Isso não funciona se person
poderia ser uma subclasse de Person
(ou se Person
é uma interface). Este é o ponto inteiro de clone, é que ele pode pode clonar o tipo adequado de forma dinâmica em tempo de execução (clone assumindo está devidamente implementado).
Person clone = (Person)person.clone();
ou
Person clone = (Person)SomeCloneUtil.clone(person); // See Bozho's answer
Agora person
pode ser qualquer tipo de Person
assumindo que clone
é devidamente aplicada.
Veja também: Como substituir adequadamente método clone . A clonagem é quebrado em Java, é tão difícil para obtê-lo direito, e mesmo quando ele faz isso realmente não oferecem muito , por isso não é realmente vale a pena.
grande tristeza: nem Cloneable / clone nem um construtor são grandes soluções: Eu não quero saber de execução CLASS !!! (Por exemplo - Eu tenho um mapa, que eu quero copiado, usando a mesma implementação MumbleMap escondido) Eu só quero fazer uma cópia, se isso é suportado. Mas, infelizmente, Cloneable não tem o método clone nele, então não há nada a qual você pode digitar-moldado sobre a qual a invocar clone () com segurança.
Qualquer que seja o melhor "copy objeto" biblioteca lá fora, é, a Oracle deve torná-lo um componente padrão da próxima versão Java (a menos que já é, em algum lugar escondido).
Claro que, se mais da biblioteca (por exemplo - Coleções) eram imutáveis, este "copiar" tarefa seria apenas ir embora. Mas então poderíamos começar a projetar programas Java com coisas como "invariantes de classe" em vez do padrão verdammt "feijão" (fazer um objeto quebrado e mutação até bom [o suficiente]).