图解ThreadLocal核心方法

1、put方法逻辑

拿到当前线程
当前当前线程的Map
getMap方法
方法内部逻辑
Map为null
createMap方法内部逻辑
创建Entry数组,原来Entry数组就是上面提到的Map,也及时ThreadLocalMap
根据创建的ThreadLocal哈希值获取下标
根据下标进行赋值
Map不为null
map.set方法内部逻辑
根据传入的ThreadLocal获取下标
根据下标赋值,这里并没有那么简单,其实Entry数组是用来解决哈希冲突的,详情见下面的哈希冲突分析
set(T value)
Thread t = Thread.currentThread()
ThreadLocalMap map = getMap(t)
getMap(Thread t)
return t.threadLocals
createMap(t, value)
t.threadLocals = new ThreadLocalMap(this, firstValue)
table = new Entry[INITIAL_CAPACITY]
int i = firstKey.threadLocalHashCode & (INITIAL_CAPACITY - 1)
table[i] = new Entry(firstKey, firstValue)
map.set(this, value)
set(ThreadLocal key, Object value)
i = key.threadLocalHashCode & (len-1)
tab[i] = new Entry(key, value)

Entry继承WeakReference
内部参数设置
key的设置为弱引用
value的设置为强引用
Entry
static class Entry extends WeakReference>
Entry(ThreadLocal k, Object v)
super(k)
value = v

for循环找到符合的下标
nextIndex就是解决哈希冲突的核心方法
内部逻辑,其实就是直接+1个索引位置
for循环内部逻辑,先拿到当前创建的ThreadLocal
当前ThreadLocal已经有值了,说明之前有人set过
直接覆盖值
重哈希法,找到正确的null下标位置,赋值即可
哈希冲突分析
for (Entry e = tab[i]; e != null; e = tab[i = nextIndex(i, len)])
nextIndex(int i, int len)
return ((i + 1 < len) ? i + 1 : 0)
ThreadLocal k = e.get()
k == key
e.value = value
tab[i] = new Entry(key, value)

2、get方法逻辑

得到当前线程
通过当前线程获取ThreadLocalMap=Map
通过threadlocal获取对应的Entry
返回entry的value(其实还是要for循环去依次查找对应的相等的threalocal,但是上上面已经走过具体的哈希冲突了,见 'put方法的哈希重复分析' )
getMap方法逻辑,直接返回一个threadLocals,其实就是个Entry数组
get()
Thread t = Thread.currentThread()
ThreadLocalMap map = getMap(t)
ThreadLocalMap.Entry e = map.getEntry(this)
return entry.value
return t.threadLocals

你可能感兴趣的:(Java集合类,java)