所以,我有这个项目,马上就要到期了,恐怕我还不太了解线程同步的概念。实际上,我似乎根本无法理解,所以如果我的问题很愚蠢 - 我提前道歉。
这个想法很简单——我有多个线程代表动物(Antilope、Lion 等扩展了 Animal 实现 Runnable),以及一个 Tile 对象的 2D 数组。动物需要在没有碰撞的情况下移动 - 如果一个人想移动到另一个人站立的瓷砖,它应该与它交互(),然后 - 如果另一个人没有死 - 等到它离开。
因此,当动物移动时,显然需要在目标图块上同步,这样没有两只动物可以同时进入一个图块。然而,当它移动时,它显然需要在它站立的瓷砖上调用 notify(),以便其他想要移动到那里的动物可以醒来。
我尝试锁定两者,但结果是动物无缘无故地死在了它们的轨道上。这是一段代码,为了澄清一点:
void move(dir direction)
{
Integer tarX = ((direction==dir.east?(x+1):(direction==dir.west?(x-1):x))); // east->x+1/west->x-1/NS->x
Integer tarY = ((direction==dir.north?(y-1):(direction==dir.south?(y+1):y))); //see above
Animal an;
synchronized(TileManager.getInstance().playField[tarX][tarY])
{
an = AnimalManager.getInstance().searchByXY(tarX, tarY);
while (an != null)
{
interact(an); //assume it's empty - if it isn't, it results in a death of target animal anyway
an = AnimalManager.getInstance().searchByXY(tarX, tarY); //possibly redundant?
if (an != null) {
try {
TileManager.getInstance().playField[tarX][tarY].wait();
} catch (InterruptedException ex) {
}
}
an = AnimalManager.getInstance().searchByXY(tarX, tarY, dir.none);
}
synchronized(TileManager.getInstance().playField[x][y])
{
int prevX = x;
int prevY = y;
x = tarX;
y = tarY;
TileManager.getInstance().playField[prevX][prevY].notify();
TileManager.getInstance().playField[x][y].notify();
}
}
}
是的,这是一团糟,我知道,而且效果也不太好。有人知道该怎么做吗?