Is there any way to find all references to an object (in Java)?
I have a cache of objects, and would like to periodically scan it to see if removing the object will cause it to be destroyed.
Is there any way to find all references to an object (in Java)?
I have a cache of objects, and would like to periodically scan it to see if removing the object will cause it to be destroyed.
There isn't a published way that exposes such an information. Let the language do the garbage collection, it is the job of the JVM vendor to implement it as specified by the language.
You could use a reference-counting scheme. Have a class that manages access to these objects, such that you need to call get() on the class (possibly with some argument) to get an instance - this should increment a counter for that instance. When your client code is done with an object, it should return it, decrementing the counter. Then all objects with a count of 0 would be referenced by no one but the container.
Of course, you would need to be very careful that you don't have any code that forgets to decrement the counter before its reference goes out of scope.
I have a cache of objects
Consider using a WeakHashMap
instead of HashMap
to get hold of them all.
Here's an extract of the API:
A hashtable-based
Map
implementation with weak keys. An entry in aWeakHashMap
will automatically be removed when its key is no longer in ordinary use. More precisely, the presence of a mapping for a given key will not prevent the key from being discarded by the garbage collector, that is, made finalizable, finalized, and then reclaimed. When a key has been discarded its entry is effectively removed from the map, so this class behaves somewhat differently from otherMap
implementations.
You might want to take a look at different reference types Java provides: strong, soft, weak, and phantom.
For cache you would normally wrap a reference into WeakReference or SoftReference and let the object be collected once there are no more strong references left.
It is not clear what you are really trying to do, so I will answer your question literally.
Is there any way to find all references to an object (in Java)?
There is no way to do this. You can go from a variable or field containing a reference, but Java does not allow you to go in the other direction. It is theoretically possible to do this kind of thing using the Java debugger mechanisms, but it would be too complicated and expensive to be practical.
I have a cache of objects, and would like to periodically scan it to see if removing the object will cause it to be destroyed.
(I assume that you mean removing the object from the cache.) Again, I don't see how you could do this in Java. The SoftReference and WeakReference classes will allow you to tell if an object has been garbage collected, but not if it will be garbage collected. Once again, this kind of thing might theoretically implementable, but it is too complex and expensive to be practical.
However, if your real goal is to implement a cache that does not stop objects being garbage collected, you should be able to do this using WeakHashMap, or by building your own cache that appropriately use WeakReference or SoftReference instances.
EDIT: I suppose that you could also consider an explicit reference counting scheme. However, such a scheme would be difficult to implement properly in Java.
Unlike C++, no destructor gets called in Java when a variable goes out of scope, or on an attribute when its parent object is garbage collected. To implement reference counting, you would need to:
try { ... } finally
blocks to deal with all possible ways that a reference counted variable can go out of scope, and finalize
methods to every class that has an attribute of the reference counted type.It is theoretically possible, but (IMO) it is too difficult to get right in all but the simplest of cases. And (just repeating myself), this is much harder to do in Java than in C++ because Java doesn't have destructors and overloading of assignment operators.