Android Framework学习之threadLocal原

2023-01-04  本文已影响0人  一只二凡子

说说ThreadLocal的原理

Framework用到ThreadLocal的地方

Looper使用ThreadLocal

Choreographer使用ThreadLocal

如果当前线程没有Choreograhper对象的话,就会调用initialValue去初始一个Choreographer对象

ThreadLocal原理

每个线程里都有一个thread对象,这个对象里有一个数组table(类似HashMap),

key:WeakReference<ThreadLocal>

value: Looper, Choreographer...

一个应用里可以定义多个threadLocal,每个ThreadLocal都有自己的hash值

//每定义一个ThreadLocal都会初始一个hash值(递增)

private final int hash = hashCounter.getAndAdd(0x61c88647*2);

从threadLocals里查找ThreadLocal(key,value):

threadLocal index = threadLocal的hash%table.length

如果对于某个threadLocal,算出来的index已经有值了,就从这个index开始往后遍历,找到空的位置,放进去,然后返回这个空位置的index

ThreadLocal原理代码解析

int index = hash & values.mask: 取余操作

this.reference == table[index]: 查看index位置上的key(weakReference) 是否和 当前threadLocal对象的reference匹配上

return (T)table[index+1]: 返回threadLocal的value,因为value是在key的下一个位置

这个方法很长,但logic简单,就两件事:

1. 通过threadLocal的initValue() 创建一个新的value

2. 在table里找一个合适的位置来存放key,value对

cleanUp():table里保存的key是threadLocal 的 weakReference,所以就有可能被回收掉,cleanUp方法就是清除已经被回收掉的key,value对

说说ThreadLocal的原理

1. 同一个ThreadLocal对象,在不同线程get返回不同value

2. Thread对象里有张表(数组),保存了ThreadLocal对象的WeakReference到value的映射关系

3. 这张表(table)是怎么实现的?

数组结构(table):[key, value, key, value, key, value, null, null, key, value, null, null,key value]

key: threadLocal对象的WeakReference

每个threadLocal对象有个hash值,这个treadLocal对象在数组中的位置:index = hash % table, 如果index位置已经有值了,就向后遍历找到null的位置放入,并返回后面这个的index

4. 是如何解决hash冲突的?

        上面已经回答了

上一篇下一篇

猜你喜欢

热点阅读