问题描述
我是Java新手。我正在研究用蜗牛填充畜栏的问题,蜗牛会根据随机的摆动方向放牧。但是输出不符合预期。
package fill;
import java.util.Random;
public class FillTheCorral extends Gate {
public static final int sRANDOM_SEED=1234;
private static final int sMAX_GATES=4;
public static void main (String[] args) {
Random randomNumber=new Random(sRANDOM_SEED);
FillTheCorral mFillTheCorral=new FillTheCorral();
Gate[] corral=new Gate[sMAX_GATES];
for (int i=0; i<corral.length; i++) {
corral[i]=new Gate();
}
do {
mFillTheCorral.setCorralGates(corral,randomNumber);
} while (!mFillTheCorral.anyCorralAvailable(corral));
}
public void setCorralGates(Gate[] gate,Random selectDirection) {
System.out.println("Initial gate setup:");
for(int i=0;i<gate.length;i++){
int randDir = selectDirection.nextInt(3)-1;
gate[i].setSwing(randDir);
System.out.println("Gate " + i + ": "+ randDir);
}
}
public boolean anyCorralAvailable(Gate[] corral) {
for(int i=0;i<corral.length;i++){
if(corral[i].getSwingDirection() == IN)
return true;
}
return false ;
}
}
class Gate {
public static final int OUT=-1;
public static final int IN=1;
public static final int CLOSED=0;
private static int mSwing;
public static
int getSwingDirection () {
return mSwing;
}
public static boolean setSwing (int dir) {
mSwing=dir;
if (mSwing == IN) return true;
if (mSwing == OUT) return true;
if (mSwing == CLOSED) return true;
return false;
}
public int thru (int count) {
if (getSwingDirection() == IN) {
return +count;
} else if (getSwingDirection() == OUT) {
return -count;
} else {
count*=0;
return count;
}
}
}
预期输出: 初始浇口设置: 登机口0:1 登机口1:1 2号登机口:1 登机门3:-1
实际输出:
初始门设置: 登机口0:1 登机口1:1 2号登机口:1 登机门3:-1
初始门设置: 登机口0:1 登机口1:-1 登机口2:0 3号门:0
初始门设置: 登机口0:-1 登机口1:0 登机口2:0 3号登机门:1
我得到的门随机方向是x3倍。
解决方法
问题是Gate的mSwing
是静态的。在for循环中调用gate[i].setSwing(randDir)
时,每次都将替换相同的静态变量。这就是为什么while循环仅在Gate 3 == 1时结束的原因。
尝试从mSwing
变量中删除静态变量。
您的问题是,在您的Gate
类中,您定义了字段mSwing
并将其获取器/设置器定义为static
。静态字段每个类仅存在一次,这意味着您创建的所有4个Gate对象将为mSwing
共享相同的值,而不是每个Gate对mSwing
都有自己的值。
更多信息,请阅读:What does the 'static' keyword do in a class?
如果将字段更改为正常的非静态字段,则将获得期望的输出:
private int mSwing;
public int getSwingDirection () {
return mSwing;
}
public boolean setSwing (int dir) {
mSwing=dir;
if (mSwing == IN) return true;
if (mSwing == OUT) return true;
if (mSwing == CLOSED) return true;
return false;
}
,
我认为问题在于您将变量 mSwing 声明为 static ,这意味着它与每个单独的对象都不相关,但与类相关,所有对象将共享相同的值。
因此,当您从对象调用 getSwingDirection()时,它将返回类静态变量,该类静态变量包含方法 setSwing()设置的最后一个值。 / p>
我添加了一个日志以向您显示结果
public boolean anyCorralAvailable(Gate[] corral) {
System.out.println("Value of getSwingDirection():");
for (int i = 0; i < corral.length; i++) {
System.out.println("corral[" +i + "]: " + corral[i].getSwingDirection());
if (corral[i].getSwingDirection() == IN)
return true;
}
return false;
}
使用静态动词的结果:
Initial gate setup:
Gate 0: 1
Gate 1: 1
Gate 2: 1
Gate 3: -1
Value of getSwingDirection():
corral[0]: -1
corral[1]: -1
corral[2]: -1
corral[3]: -1
Initial gate setup:
Gate 0: 1
Gate 1: -1
Gate 2: 0
Gate 3: 0
Value of getSwingDirection():
corral[0]: 0
corral[1]: 0
corral[2]: 0
corral[3]: 0
Initial gate setup:
Gate 0: -1
Gate 1: 0
Gate 2: 0
Gate 3: 1
Value of getSwingDirection():
corral[0]: 1
Process finished with exit code 0
没有静态修饰符的结果:
Initial gate setup:
Gate 0: 1
Gate 1: 1
Gate 2: 1
Gate 3: -1
Value of getSwingDirection():
corral[0]: 1
Process finished with exit code 0
从 mSwing 中移除 static 修饰符,然后从方法 setSwing()和 getSwingDirection()中移除你的问题。