0
public class Stav implements Cloneable{
private int[] pole;

public Stav(int[] pole){
    this.pole = pole;
}
public Stav(Stav a){
    this.pole = a.pole;
}
public void move(boolean left){
    int empty = findEmpty();
    if(left){
        this.pole[empty] = this.pole[empty - 1];
        this.pole[empty - 1] = 0;
    }
    else{
        this.pole[empty] = this.pole[empty + 1];
        this.pole[empty + 1] = 0;
    }
}

Jednotka pom = fronta.remove();
Stav nStav = new Stav(pom.getStav().getPole());
Stav pomStav = new Stav(nStav);

当我打电话时

pomStav.move(false);

nStav 的值将与 pomStav 相同...有人可以帮助我吗?我在代码中有更多方法,但它太长了,所以我没有像 findEmpty 等那样复制这里。

4

3 回答 3

1
public Stav(Stav a){
    this.pole = a.pole;
}

当您调用它时,当您复制对对象的引用时,底层int[] pole在两个实例之间共享。不要复制引用,而是创建一个新数组并复制值:

public Stav( Stav a )
{
    this.pole = new int[ a.pole.length ];
    for( int i = 0; i < this.pole.length; ++i )
        this.pole[ i ] = a.pole[ i ];
}
于 2014-11-03T23:26:52.697 回答
0

如果您希望您的Stav实例彼此独立,那么您在这里遇到了问题

public Stav(Stav a){
    this.pole = a.pole;
}

... 和这里

Stav nStav = new Stav(pom.getStav().getPole());

...或者,在这里

public Stav(int[] pole){
    this.pole = pole;
}

. 效果是您为您的Stav实例提供对其成员的相同数组的引用。pole如果你想让它们独立,那么你必须给它们数组的副本。一种方法是像这样编写构造函数:

public Stav(int[] pole){
    this.pole = ((pole == null) ? null : pole.clone();
}
public Stav(Stav a){
    this(a.pole);
}
于 2014-11-03T23:27:09.967 回答
0

您的复制构造函数(以及默认的“克隆”方法)正在执行浅拷贝:

this.pole = a.pole;

在上面的语句之后, this.pole 和 a.pole 都是对同一个数组的引用。如果你想做一个稍微深一点的副本,你可以这样做

this.pole = Arrays.copyOf (a.pole, a.pole.length);

在此操作之后,对数组的更改将不会在实例之间传播 - 尽管对数组内容的更改将是如果它们是非原始数组。

如果你希望你的对象在克隆时也做一个深拷贝,你需要重写 clone() 方法:

public Object clone() {
  return new Stav(this);
}

(请注意,克隆存在许多问题 -如果您要进行涉及克隆的重要工作,我强烈建议您阅读Effective Java中有关克隆的章节。

于 2014-11-03T23:29:04.343 回答