ThreadLocal 与内存泄漏
【Q】为什么不能使用强引用?
先看看使用强引用会出现什么问题。
ThreadLocalMap 中,value 作为一个本地变量,应该不会说总在使用,因此用完之后最好清理这个 Entry。
如果线程执行很快,线程退出后 ThreadLocalMap 不存在了自然不用再管其内部属性了;但如果是长时间存在的线程,在并发量大的情况下,每个线程都持有一个无用对象无法回收,造成内存泄漏。(当然可以手动回收)
ThreadLocalMap 使用弱引用的 key 是一个很大的进步,能够在 set 与 get 的过程中检测到无效的 key,从而清理连续段中包含无效 key 的 Entry。
但这种清理工作并不是每次都及时的,对于长时间运行的线程,如果 key 引用的对象被回收之后,不再调用 set 与 get 方法,那么 value 对象就一直不会清理,将造成内存泄漏。
解决办法就是用完之后调用 remove 方法进行清理。
PS:如果 ThreadLocal 对象是 static 类型,弱引用将形同虚设,类似于上述强引用的问题,可以手动回收。