【源码解析】通过源码解析 ThreadLocal 内存泄漏, 弱引用, 以及设计原因.
已知
- 每个 Thread 在创建的时候, 都会包含一个 ThreadLocalMap.
- ThreadLocal 本质是将 value 信息存入 ThreadLocalMap 中, key 是 ThreadLocal (弱引用), value 是强引用.
- ThreadLocalMap 本质是采用内部实现的 Entry[] 数组存储数据 .
- Entry 继承了 WeakReference,(弱引用本质). 其中, key 值为父类的 referent (弱引用), value 为 Entry 内部自定义的对象.
- 弱引用特点: 系统 GC 的时候, 会直接回收弱引用对象.
- ThreadLocalMap 为 ThreadLocal 的静态内部类, 外部无法直接调用.
- ThreadLocalMap 是与 Thread 直接绑定的, 所以, 如果不是使用线程池, 是不用担心内存泄漏的, 会在 Thread 销毁的时候一并销毁
源码解析 set()
public void set(T value) {
Thread t = Thread.currentThread();
ThreadLocalMap map = getMap(t);
if (map != null) {
map.set(this, value);
} else {
createMap(t, value);
}
}
private void set(ThreadLocal<?> key, Object value) {
Entry[] tab = table;
int len = tab.length;
int i = key.threadLocalHashCode & (len-1);
for (Entry e = tab[i];
e != null;
e = tab[i = nextIndex(i, len)])