Java:References
Java引用类型
Strong References
默认的引用方式,即通过MyClass obj = new MyClass ();
这种方式赋值的对象,如果其存在active引用(从GC Root reachable)的话,是不会被回收的。如果内存不够,会抛出OOM异常。
Weak References
如果一个对象只能被弱引用访问(不存在强引用或者软引用的情况),那么下一次GC将被清理掉。
其主要的使用场景是实现canonicalizing mappings。即对于一个特定的value,map中只有一个instance。
Soft References
软引用的对象在JVM内存不足的时候会被回收掉。
Phantom References
作用
PhantomReference(虚引用) 无法直接获取被引用的对象,必须跟ReferenceQueue一起使用。PhantomReference最弱,发生GC时会被回收,当JVM执行完finalize
之后,对象会被放到ReferenceQueue中。
Gfg g = new Gfg();
ReferenceQueue<Gfg> refQueue = new ReferenceQueue<>();
PhantomReference<Gfg> phantomRef = new PhantomReference<>(g, refQueue);
// 当g(强引用)不继续存在之后,对象就会被可以回收了
// 但在对象
g = null;
//It always returns null.
g = phantomRef.get();
使用场景
其使用场景主要有两种:
- 检测对象何时被回收,例如在执行对内存敏感的任务的时候,等待大对象回收了再开始新的任务
- 避免直接执行finalize,
Object.finalize()
在Java9中被标为Deprecated了,The Cleaner and PhantomReference provide more flexible and efficient ways to release resources when an object becomes unreachable.
直接执行finalize有什么问题呢?
Finalization can lead to performance issues, deadlocks, and hangs. Errors in finalizers can lead to resource leaks; there is no way to cancel finalization if it is no longer necessary; and no ordering is specified among calls to finalize methods of different objects.