先了解下ThreadLocal在运行时候的示意图:
栈中线程引用通过强引用指向堆中的Thread对象和ThreadLocalMap(value实际存放在ThreadLocalMap里面的Entry)
Entry类的源码:
Entry.get()方法获取到的引用是弱引用,也就是当ThreadLocal被GC回收的时候,entry可能没有被GC,这就造成了内存泄露
,那entry什么时候被回收呢?
只有当current thread终止时候,这个entry才会被回收。
结论:
比如在使用线程池,线程结束是不会销毁的,而是会再次使用,这样当线程没有终止,并且ThreadLocal是null的时候,会造成内存泄露
解决:每次从这个线程离开,get到值后,调用remove方法,主动将entry删除
另外,ThreadLocal的get,set 都会尝试去删除过期的entry
参考:
https://www.cnblogs.com/onlywujun/p/3524675.html