Java 引用队列中的PhantomReference是否阻止PhantomReference成为GC';D
我正在使用LWJGL库,不幸的是,每当场景图中的节点需要死亡时,我需要自己释放纹理/vbo缓冲区,我甚至不能使用finalize()方法来完成此操作,因为我不能保证它将在opengl libs期望的同一线程中执行 所以我用的是幻影参考。在我的场景图节点中,我将其放入构造函数中:Java 引用队列中的PhantomReference是否阻止PhantomReference成为GC';D,java,Java,我正在使用LWJGL库,不幸的是,每当场景图中的节点需要死亡时,我需要自己释放纹理/vbo缓冲区,我甚至不能使用finalize()方法来完成此操作,因为我不能保证它将在opengl libs期望的同一线程中执行 所以我用的是幻影参考。在我的场景图节点中,我将其放入构造函数中: phantomReference = new ScenePhantomReference(this, Game.phantomReferenceQueue); Game.phantomReferenceList.add(
phantomReference = new ScenePhantomReference(this, Game.phantomReferenceQueue);
Game.phantomReferenceList.add(phantomReference);
正如您在第二行中看到的,我已将phantomReference添加到main类的列表中。我的逻辑是,当节点被解除引用时,phantomReference不会被垃圾收集,因为在主类中仍然有一个引用
是否需要将其添加到这样的列表中?或者它会不会从GC中保留(可能Game.phantomReferenceQueue会保留对它的引用?)
这是一个很难测试的问题,我可以删除列表,但是GC可能只是处理在phantomReference之前被监视的对象,并使其看起来像列表是多余的,而实际上并非如此。我会怀疑任何不同的虚拟机实现或版本可能会以相反的方式来实现它。免责声明:我从未使用过PhantomReference 然而,我确实读过,也读过,等等
其中
scene
是代码中的ScenePhantomReference
(即,您应该重构代码,使ScenePhantomReference
成为名称,例如scene
,您将其实例化为scene
,然后使用上面的行获取该对象的幻影引用的句柄)。
如果您不将PhantomReference
添加到列表
,则不会引用PhantomReference
对象,因此它会立即被GC'd,并且永远不会进入队列。我使用了它们,根据经验,我可以说您需要维护一个引用,以防止它被GC'd。我做过一次,并使用IdentityHashMap作为一个集合(值总是一个虚拟对象)。这比List/HashMap快。编辑:下面是代码:这是在:已注册的引用对象与其队列之间的关系是单边的。也就是说,队列不跟踪已注册的引用。如果已注册的引用本身无法访问,则它将永远不会排队。使用引用对象的程序负责确保对象重新访问只要程序对其引用对象感兴趣,就可以访问main”。
PhantomReference scenePhantomRef = new PhantomReference(scene, phantomQueue);