我在GameWorld中有一系列游戏对象,他们可以从那个世界中删除。问题是某些游戏对象引用了其他游戏对象。例如。 Player类引用了Bird。 Bird会从GameWorld中随机删除,但Player仍然会引用它。我目前进行空检查以检查GameObject是否仍然有效并且在世界上。但是,从数组中删除对象不会使该引用为null。那我怎么能把它变成空?
以下是一个例子:
// GameWorld creates bird
ArrayList<Object> gameObjects = new ArrayList<>();
Object bird = new Object();
gameObjects.add(bird);
// Player references it
Object referencedBird = gameObjects.get(0);
// later in GameWorld, another scope, there is no access to the 'bird' object, trying to remove the bird from the world
Object objectToRemove = gameObjects.get(0);
gameObjects.remove(0);
objectToRemove = null;
// back in the Player class
Debug.log("is null " + (referencedBird == null)); // false! I need it to be true
答案 0 :(得分:6)
您无法制作对象 null
,您只能制作参考null
。更新对象的一个引用不会更改对同一对象的其他引用。
想想我们在手机中拥有相同人物的号码:如果我删除号码,则不会从手机中删除。如果我们都删除它,那个人的电话号码就不会存在:我们俩都不能打电话给他们。
你唯一能做的就是:
referencedBird = null
; gameObjects.get(0)
而不是通过referencedBird
变量来引用它。答案 1 :(得分:1)
好的,因为安迪指出你不能破坏一个物体,你仍然可以解决这个问题。
interface RemoveAble<T>{
boolean isRemoved();
T prepareRemoveAndGet();
}
class Bird implements RemoveAble<Bird>{
boolean shouldRemove = false;
@Override
public boolean isRemoved() {
return shouldRemove;
}
@Override
public Bird prepareRemoveAndGet() {
shouldRemove = true;
return this;
}
}
并像这样使用它:
// GameWorld creates bird
ArrayList<RemoveAble> gameObjects = new ArrayList<>();
Bird bird = new Bird();
gameObjects.add(bird);
// Player references it
Bird referencedBird = gameObjects.get(0);
// later in GameWorld, another scope, there is no access to the 'bird' object, trying to remove the bird from the world
Object objectToRemove = gameObjects.get(0).prepareRemoveAndGet;
// back in the Player class
Debug.log("is null " + (referencedBird.isRemoved == true)); // false! I need it to be true
然后自己null
e.g。
if(referencedBird.isRemoved) referencedBird = null;
答案 2 :(得分:0)
首先,您需要更好地了解Java变量的工作原理:
我将变量设置为null,这根本不会影响它背后的对象。您需要以某种方式使引用的对象无效(使用布尔变量),或者更好的解决方案是始终直接从ArrayList
获取对象。
答案 3 :(得分:0)
与java中的C和C ++不同,你不能直接操作内存,唯一的选择就是删除对obj的所有强(常规)引用,并留给JVM,以便在需要内存时将其从内存中删除。
// GameWorld creates bird
ArrayList<Object> gameObjects = new ArrayList<>();
Object bird = new Object();
gameObjects.add(bird);
// a weak reference to array Item
WeakReference<Object> referencedBird = new WeakReference(gameObjects.get(0));
// manipulating and accessing array item via weak reference
referencedBird.get().toString();
// after this remove there is no strong reference to array element (0) and it is available for JVM to revoke
//memory allocated to it in up-coming garbage collection cycle
gameObjects.remove(0);
//garbage collection may remove the obj from memory so this method may return null
referencedBird.get();
此外,您还可以通过制作类型为WeakReference的数组来制作游戏对象列表,提高内存效率
ArrayList<WeakReference> weakReferenceToGameObjects = new ArrayList<>();
Object bird1 = new Object();
weakReferenceToGameObjects.add((WeakReference) bird1);
bird1 = null;
// now if you try to get the element you may get null!
weakReferenceToGameObjects.get(0).get();