ThreadLocal如何回收value,什么时候回收?(学习笔记)
1)ThreadLocal如何回收value,什么时候回收?
从ThreadLocal中的内部类分析:
①
static class ThreadLocalMap { /** * The entries in this hash map extend WeakReference, using * its main ref field as the key (which is always a * ThreadLocal object). Note that null keys (i.e. entry.get() * == null) mean that the key is no longer referenced, so the * entry can be expunged from table. Such entries are referred to * as "stale entries" in the code that follows. */ ...... }
ThreadLocalMap是一个定制的哈希映射,仅适用于维护线程本地值。为了帮助处理非常大和长期使用的用法,哈希表条目使用weakreferences作为键。但是,由于不使用引用队列,因此只有当表开始耗尽空间时,才保证删除过时的条目。(源码注释)
②
static class Entry extends WeakReference<ThreadLocal<?>> { /** The value associated with this ThreadLocal. */ Object value; Entry(ThreadLocal<?> k, Object v) { super(k); value = v; } }
ThreadLocalMap是使用ThreadLocal的弱引用作为Key的(注意:Value并非弱引用),Key只能是ThreadLocal对象,从而实现了变量访问在不同线程中的隔离。当一个ThreadLocal失去强引用,生命周期只能存活到下次gc前,此时ThreadLocalMap中就会出现key为null的Entry,当前线程无法结束,这些key为null的Entry的value就会一直存在一条强引用链,造成内存泄露。
解决方案:
建议将ThreadLocal变量定义成private static的,在调用ThreadLocal的get()、set()方法完成后,再调用remove()方法,手动删除不再需要的ThreadLocal。
2)ThreadLocal为什么会产生脏数据?
因为Thread Pool是一把双刃剑,好处略,坏处之一:
如果Thread是从Thread Pool中取出,它可能会被复用,此时就一定要保证这个Thread在上一次结束的时候,其关联的ThreadLocal被清空掉,否则就会串到下一次使用。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· 浏览器原生「磁吸」效果!Anchor Positioning 锚点定位神器解析
· 没有源码,如何修改代码逻辑?
· 全程不用写代码,我用AI程序员写了一个飞机大战
· DeepSeek 开源周回顾「GitHub 热点速览」
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· 记一次.NET内存居高不下排查解决与启示
· 白话解读 Dapr 1.15:你的「微服务管家」又秀新绝活了