* 主要是通过ThreadLocal 内部的静态内部类 ThreadLocalMap 实现的,在使用ThreadLocal 的时候,是先通过当前线程得到 ThreadLocalMap 对象.
* ThreadLocalMap内部是一个 Entry[] 数组存储的,Entry[] 内部存储了是以 ThreadLocal的 threadLocalHashCode 为键,以本地线程变量为值的 K-V值对,ThreadLocal 就是当前线程的访问 ThreadLocalMap 的入口,每一个ThreadLocal 对象都包含了一个独一无二的 threadLocalHashCode 值,使用这个值就可以在线程ThreadLocalMap 的 K-V 值对中找到对应的本地线程变量。
* 这个值对是以弱引用包裹起来的,为了在不需要的时候 让系统进行回收,不过最好还是手动调用 remove 移除。
![](https://markdown-1258186581.cos.ap-shanghai.myqcloud.com/20200309153332.png)
后根据 ThreadLocalMap 对象以 ThreadLocal 对象获得 ThreadLocal 对象对应的 value 值。在获取 ThreadLocalMap 对象的时候,是通过当前线程的对象获得的,所以保证了一个线程有一个 ThreadLocalMap 对象,保证了线程隔离,然后再不同的线程中根据不同的 ThreadLocal 对象获取具体对应的值。
[Android的消息机制之ThreadLocal的工作原理](https://blog.csdn.net/singwhatiwanna/article/details/48350919)
[参考地址](https://chenjiayang.me/2018/01/26/threadlocal-source-code/)
首先是在 Therad 类中有一个属性
~~~
/* ThreadLocal values pertaining to this thread. This map is maintained
* by the ThreadLocal class. */
ThreadLocal.ThreadLocalMap threadLocals = null;
~~~
![](https://markdown-1258186581.cos.ap-shanghai.myqcloud.com/20190617235233.png)
ThreadLocalMap:
![](https://markdown-1258186581.cos.ap-shanghai.myqcloud.com/20190617235329.png)
这个 Map 的 key 是 ThreadLocal 变量,value 为用户的值。
1. Thread类中有一个成员变量叫做 ThreadLocalMap ,它是一个 Map,虽然叫 map,但是内部确实用数组来实现的,索引为 ThreadLocalHashCode 值。存储的是一个弱引用,弱引用里面是具体的值。
2. 每个线程拥有自己的声明为 ThreadLocalMap 类型的变量,所以这个类的名字叫 'threadLocals',一个线程对应一个 ThreadLocal ,但是和 ThreadLocal 对应的值可以有很多个。
3. 此变量生命周期是由该线程决定的,get或者set方法在第一次执行的时候进行初始化,在线程的`exit()`方法执行的时候,进行销毁。
4. 由ThreadLocal和 ThreadLocalMap 两者结合的工作原理决定了:每个线程独自拥有一个变量,并非共享或者拷贝
- Java 面试题
- String、StringBuffer、StringBuilder 的区别?
- Java 中的四种引用
- 接口和抽象类的本质区别
- 集合框架
- 集合概述
- ArrayList 源码分析
- LinkedList 源码分析
- HashMap 源码分析
- LinkedHashMap 源码分析
- Android提供的 LruCache 的分析
- LinkedList 和 ArrayList 的区别
- 多线程
- 实现多线程的几种方式
- 线程的几种状态
- Thread 的 start() 和 run() 的区别
- sleep() 、yield() 和 wait() 的区别 ?
- notify() 和 notifyAll() 的区别?
- 保证线程安全的方式有哪几种?
- Synchronized 关键字
- volatile 和 synchronized 的区别?
- 如何正确的终止一个线程?
- ThreadLocal 原理分析
- 线程池
- 多线程的三个特征
- 五种线程池,四种拒绝策略,三种阻塞队列
- 给定三个线程如何顺序执行完以后在主线程拿到执行结果
- Java 内存模型
- 判定可回收对象算法
- equals 与 == 操作符
- 类加载机制
- 类加载简单例子
- 算法
- 时间、空间复杂度
- 冒泡排序
- 快速排序
- 链表反转
- IO
- 泛型
- Kolin 面试题
- Android 面试题
- Handler 线程间通信
- Message、MessageQueue、Looper、Handler 的对象关系
- Handler 使用
- Handler 源码分析
- HandlerThread
- AsyncTask
- IntentService
- 三方框架
- Rxjava
- rxjava 操作符有哪些
- 如何解决 RxJava 内存泄漏
- Rxjava 线程切换原理
- map和 flatmap 的区别
- Databinding引起的 java方法大于 65535 的问题
- Glide
- Glide 的缓存原理
- Glide 是如何和生命周期绑定的?不同的Context 有什么区别?
- Glide 、Picasso 、的区别,优劣势,如何选择?
- Jetpack
- 源码分析
- EventBus
- EventBus 源码分析
- RxBus 替代 EventBus
- OkHttp
- OkHttp 源码分析
- OkHttp 缓存分析
- RxPermission
- RxPermission 源码分析
- Retrofit
- create
- Retrofit 源码分析
- 优化
- 启动优化
- 布局优化
- 绘制优化
- 内存优化
- 屏幕适配
- 组件
- Activity
- Frgment
- Service
- ContentProvider
- BroadcastReceiver
- 进程间通信
- Binder机制和AIDL
- AILD 中的接口和普通的接口有什么区别
- in、out、inout 的区别
- Binder 为什么只需要拷贝一次
- 在android中,请简述jni的调用过程
- 生命周期
- Activity 生命周期
- Fragment 生命周期
- Service 生命周期
- onSaveInstanceState() 与 onRestoreIntanceState()
- 前沿技术
- 组件化
- 模块化
- 插件化
- 热更新
- UI - View
- Android 动画
- 事件分发机制
- WebView
- 系统相关
- 谈谈对 Context 的理解
- Android 版本
- App应用启动流程
- App 的打包
- App 的加固
- App 的安装
- Activity 启动流程
- ClassLoader
- Lru 算法加载 Bitmap 三级缓存原理
- Parcelable 和 Serializable 的区别
- Activity的启动流程
- 相关概念
- 网络相关
- Http
- Https
- Http 和 Https 的区别
- 为什么要进行三次握手和四次挥手?
- OkHttp使用Https访问服务器时信任所有证书
- 设计模式
- 单例模式
- 构建者模式
- 工厂模式
- 外观模式
- 代理模式