@[toc]
前言
- ThreadLocal 想必大家都非常熟悉了,这个不再多做ThreadLocal 的使用案例,,如果有不熟悉的小伙伴 可以阅读
- https://blog.csdn.net/qq_41977838/article/details/105766305
ThreadLocal的源码
本节 我们详细了解ThreadLocal的源码,让大家更为了解ThreadLocal
ThreadLocalMap
ThreadLocal中的嵌套内部类ThreadLocalMap,这个类本质上是一个map,和HashMap之类的实现相似,依然是key-value的形式,其中有一个内部类Entry,其中key可以看做是ThreadLocal实例,但是其本质是持有ThreadLocal实例的弱引用
ThreadlocalMap 会发现他是ThreadLocal 的一个内部类,
会发现他有一个Entry
**Entry继承WeakReference,使用弱引用,可以将ThreadLocal对象的生命周期和线程生命周期解绑,持有对ThreadLocal的弱引用,可以使得ThreadLocal在没有其他强引用的时候被回收掉,这样可以避免因为线程得不到销毁导致ThreadLocal对象无法被回收。并且
他是 以key value 形式的Entry **
有兴趣的同学可以打开 底层源码看下具体实现
initialValue
initialValue ThreadLocal初始化的方法,默认为 null ,可以重写
get 方法
会发现他把 Thread.currentThread(); 传到 getMap() 方法中,
调用Thread 类 中定义的 Threadlocal.ThreadlocalMap() 返回一个map
判断当前线程的map是否存在,不为空, 获取当前Entry 实例,
判断这个键值对是否为空
如果不是空,就返回对应的value值
此处是当前线程的map不存在,返回setInitialValue,为空返回初始化值
这里有个非常重要的知识,initialValue 是使用懒加载 ,只有调用 get 的时候才会 使用initialValue 方法,在 new ThreadLocal 中是不会初始化的
private T setInitialValue() {
//获取初始化值,默认为null(如果没有子类进行覆盖)
T value = initialValue();
Thread t = Thread.currentThread();
ThreadLocalMap map = getMap(t);
//不为空不用再初始化,直接调用set操作设值
if (map != null)
map.set(this, value);
else
//第一次初始化,createMap在上面介绍set()的时候有介绍过。
createMap(t, value);
return value;
}
接下来我们看下 set的方法
set方法
调用Thread 类 中定义的 Threadlocal.ThreadlocalMap() 返回一个map
判断当前线程的map是否存在,如果ThreadLocal中有这个map,就把当前类和对应的值传进去
如果没有这个map,就新建一个t线程的ThreadLocalMap,并将value值传进去
remove方法
remove方法就比较简单了