Copiando objetos

13 respostas
ailujana

olá pessoal, eu gostaria de saber como faço para copiar um objeto (instanciando um novo objeto para guardar a cópia).

a questão é a seguinte:
tenho um vetor de objetos vet1[10] instanciado, agora quero criar uma cópia deste vetor, guardando a informação dele em um segundo vetor vet2[10]…

como vocês ja devem saber, o código a seguir não funciona, pois ele faz com que os objetos de vet2 apontem para o local da memoria onde estão os objetos de vet1:

for(int x; x<10; x++){
    vet2[x]=vet1[x];
}

como faço então para que vet2 receba os valores de vet1 sem apontar para o mesmo? (imagino que exista uma solução melhor do que passar cada um dos atributos na mão)

Obrigada :slight_smile:

13 Respostas

gpd38

Classe A{

Object obj1, obj2;

obj1 = new Object();
obj2 = new Object();

obj2 = obj1;

}

B

Se você quer criar uma copia de um objeto (praticamente o mesmo objeto, mas uma nova referência), implemente a interface Cloneable e substitua o método clone() de Object. Note que se sua classe não implementar a interface, chamar este método resultará em uma CloneNotSupportedException.

public class SuaClasse implements Cloneable {

    @Override
    public SuaClasse clone() {
        try {
            return (SuaClasse) super.clone();     // clone() de Object, retorna uma cópia, atributo por atributo.
        } catch (CloneNotSupportedException e) {
            throw new AssertionError();           // Não pode acontecer.
        }
    }

    public static void main(String[] args) {
        SuaClasse sc = new SuaClasse();
        System.out.println(sc != sc.clone());     // true
    }
}
ailujana

gpd38:
Classe A{

Object obj1, obj2;

obj1 = new Object();
obj2 = new Object();

obj2 = obj1;

}

quando você faz “obj2 = obj1;”, na verdade voce esta fazendo com que o obj2 aponte para o mesmo lugar do obj1 na memoria, sendo assim, todas as alterações que forem feitas em obj2, tambem irão modificar o obj1… O que eu quero é que os dois objetos fiquem INDEPENDENTES um do outro, ou seja, caso eu modifique o obj2, o obj1 deve permancer intacto.

M

Esse código funciona sim. E ele copia cada elemento de vet1 para vet2.

vet2 teria a mesma referencia que vet1 se o código fosse assim:
vet2 = vet1;
Mais duas coisas: 1-) do jeito como está, na terminologia Java, vet1 e vet2 são chamados de arrays e não de vetores 2-) sim há formas melhores de trabalhar com arrays, conheça Collections, Arrays, ArrayList... Veja o exemplo:
public class TesteArray01 {

	public static void main(String[] args) {

		int i;
		int[] arr01 = new int[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
		int[] arr02 = new int[10];
		int[] arr03 = new int[10];
		int[] arr04;

		// copiando o conteúdo de arr01 para arr02
		for (i = 0; i < arr02.length; i++) {
			arr02[i] = arr01[i];
		}

		// imprimindo arr01
		System.out.print("arr01: " + arr01 + " {");
		for (i = 0; i < arr01.length; i++) {
			System.out.print(arr01[i] + ", ");
		}
		System.out.println("}");

		// imprimindo arr02
		System.out.print("arr02: " + arr02 + " {");
		for (i = 0; i < arr02.length; i++) {
			System.out.print(arr02[i] + ", ");
		}
		System.out.println("}");

		// arr03 recebe a mesma referencia que arr02
		arr03 = arr02;

		// imprimindo arr03
		System.out.print("arr03: " + arr03 + " {");
		for (i = 0; i < arr03.length; i++){
			System.out.print(arr03[i] + ", ");
		}
		System.out.println("}");

		// copiando o conteúdo de um array utilizando Arrays
		arr04 = Arrays.copyOf(arr03, arr03.length);

		// imprimindo arr04
		System.out.print("arr04: " + arr04 + " {");
		for (i = 0; i < arr04.length; i++){
			System.out.print(arr04[i] + ", ");
		}
		System.out.println("}");

		// imprimindo arr05
		int[] arr05 = new int[]{1, 2, 3,};
		System.out.println("Tamanho de arr05 é " + arr05.length);
	}
}
Ficou sobrando uma vírgula na impressão dos arrays, mas veja o array arr05. Em Java isso é válido!

Boa sorte!

ailujana

Obrigada mspereira, eu achei que deste jeito o programa fosse copiar a referência do objeto, mas eu estava errada…

beibin, implementar a classe Cloneable também funciona, mas do jeito que o mspereira disse é muito mais pratico, mas obrigada assim mesmo!

:slight_smile:

B

Acabei de descobrir aqui que é possível clonar arrays diretamente…

int[] x = { 1, 2, 3 }; int[] y = x.clone(); System.out.println(x == y); // false

Dá menos trabalho que implementar tudo.

Mancada minha, não ter visto isso antes. :XD:

M

Sim, clonar um array funciona perfeitamente.

peczenyj

deve funcionar bem no caso de primitivos mas objetos complexos provavelmente o melhor é copia-los explicitamente.

Pessoalmente, prefiro um construtor que recebe um objeto do mesmo tipo do que usar o metodo clone.

M

peczenyj:
deve funcionar bem no caso de primitivos mas objetos complexos provavelmente o melhor é copia-los explicitamente.

Pessoalmente, prefiro um construtor que recebe um objeto do mesmo tipo do que usar o metodo clone.


Mas nesse caso, o construtor não estaria recebendo a cópia da referência?

Como você faria para “duplicar” o objeto.

Grato.

discorpio

Boa tarde a todos.

Concordo com o nosso amigo Peczenyj, até porque, o que a nossa amiga Ailujana quer fazer chama-se [color=blue]“Persistência de Dados”[/color], e nesse caso, o ideal é voce criar duas classes, assim voce pode ter a opção de instanciar apenas uma classe contendo um método para instanciar a primeira classe e conter dados de classes diferentes, dados estes encapsulados e utilizando-se dos métodos Getters e Setters, afinal para que serve os mesmos, senão vejamos.

// Implementando a primeira classe
  public class PrimeiraClasse {

    private int[] arrayint;

    public int[] getArrayint() {
        return arrayint;
    }

    public void setArrayint(int[] arrayint) {
        this.arrayint = arrayint;
    }

  }
  // Implementando a segunda classe;
  public class SegundaClasse {

    private int[] arrayint;
    private PrimeiraClasse primeiraclasse = null;

    public int[] getArrayint() {
        return arrayint;
    }

    public void setArrayint(int[] arrayint) {
        this.arrayint = arrayint;
    }

    public PrimeirClasse getPrimeiraclasse(){
       // Evitando o NullPointer
       if (primeiraclasse==null) primeiraclasse = new PrimeiraClasse():
       return primeiraclasse;
    }

    public void setPrimeiraclasse(PrimeirClasse primeiraclasse){
       this.primeiraclasse = primeiraclasse;
    }
}

Agora vamos instanciar somente a segunda classe:

public class Main {

    public static void main(String args[]){
        SegundaClasse segunda = new SegundaClasse();
        int[] array = {0,1,2,3,4,5,6,7,8,9};

        // Guardando no primeiro array
        segunda.setArrayint(array);
        System.out.println("Imprimindo o primeiro array");
        imprimeDados(segunda.getArrayint());
       
        // Copiando para primeira classe
        segunda.getPrimeiraclasse().setArrayint(array);
        System.out.println("Imprimindo o segundo array");
        imprimeDados(segunda.getPrimeiraclasse().getArrayint());


        // modificando array e armazenando no primeiro array
        array = new int[]{10,11,12,13,14,15,16,17,18,19,20};
        segunda.setArrayint(array);
        System.out.println("Imprimindo o primeiro array modificado");
        imprimeDados(segunda.getArrayint());

        System.out.println("Imprimindo o segundo array intacto");
        imprimeDados(segunda.getPrimeiraclasse().getArrayint());
    }

    public static void imprimeDados(int[] dados){
        for (int i=0; i<dados.length; i++){
            System.out.print(dados[i]+",");
        }
        System.out.println();
    }

}

Pessoal, devo chamar a atenção de vocês [color=blue]que é assim que o Java trabalha[/color] :idea:, instanciando classes dentro de outras classes, pois quem se lembra deste método do JFrame :?:

....
  getContentPane().add(.......);
  getContentPane().setLayout(.....);
  ....

Feliz Páscoa a todos.>>

peczenyj

mspereira:
peczenyj:
deve funcionar bem no caso de primitivos mas objetos complexos provavelmente o melhor é copia-los explicitamente.

Pessoalmente, prefiro um construtor que recebe um objeto do mesmo tipo do que usar o metodo clone.


Mas nesse caso, o construtor não estaria recebendo a cópia da referência?

Como você faria para “duplicar” o objeto.

Grato.

Pessoa sabe como duplicar

class Pessoa{
	private String nome;
	private int idade;
	
	public Pessoa(String nome,int idade){
		this.nome = nome; 
		this.idade = idade;	
	}
	
	public Pessoa(Pessoa p){
		this.nome = p.getNome(); 
		this.idade = p.getIdade();	
	}
	// getters + setters
}
M

peczenyj:
Pessoa sabe como duplicar

Ok! Valeu!

M
Achei isso esse código aqui.
class ArrayCopyDemo {
    public static void main(String[] args) {
        char[] copyFrom = { 'd', 'e', 'c', 'a', 'f', 'f', 'e', 'i', 'n', 'a', 't', 'e', 'd' };
        char[] copyTo = new char[7];

        System.arraycopy(copyFrom, 2, copyTo, 0, 7);
        System.out.println(new String(copyTo));
    }
}
Boa sorte!
Criado 3 de abril de 2010
Ultima resposta 7 de abr. de 2010
Respostas 13
Participantes 6