首页 > 编程语言 >ThreadLocal源码解析

ThreadLocal源码解析

时间:2024-04-02 21:33:12浏览次数:22  
标签:ThreadLocalMap 对象 回收 ThreadLocal 源码 引用 哈希 解析

方法

三个主要方法:get set remove
讲三个方法前,现需要知道Thread,ThreadLocal,ThreadLocalMap三个之间的关系,首先ThreadLocalMap虽然是ThreadLocal中定义的静态内部类,但实际的 ThreadLocalMap 实例是作为 Thread 对象的一个字段存在的。这样设计的目的是允许每个线程存储自己独有的线程局部变量,而这些变量通过各自的 ThreadLocal 对象来访问。
ThreadLocalMap中key为ThreadLocal对象本身,value为该线程存储的变量的值。

get、set方法:ThreadLocal 会通过当前线程(Thread.currentThread())来访问或修改与当前线程关联的 ThreadLocalMap
image.png
image.png
remove方法:调用ThreadLocalMap的remove方法,清除对应的元素之后,调用expungeStaleEntry方法(从当前位置开始遍历,直到遇到空槽结束;这期间1.清理垃圾;2.将错位的元素放到离理想位置最近的地方,使Entry数组更紧凑)。
image.png
image.png

ThreadLocalMap

  1. 初始容量必须是2的幂

  2. 高效:与运算比取模运算更快

  3. 均匀分布:好的哈希函数会生成均匀分布的哈希值,这意味着低位的组合也将均匀分布。因此,使用哈希值的低位可以帮助实现均匀地将元素分布到哈希表的各个位置,减少冲突。

  4. 简化扩容:如果容量是2的幂,那么扩容后要么在原位置,要么移动到新位置(在原位置+原容量,只需要设置一个新的位),这使得在扩容时重新分配元素变得非常简单和高效;如果容量不是2的幂,元素在新哈希表中的位置不能简单通过保留原哈希值的低位来确定,就需要对每个值进行重新应用完整的哈希函数来确定扩容后的新位置。

例子:
假设有一个哈希值 101100(44 十进制)和一个容量为 16(10000 二进制)的哈希表,计算索引的操作如下:
101100& 01111
------

结果 00100

  1. 扩容时,使用较低的阈值以避免滞后(ThreadLocalMap 0.75)

为什么不能满阈值之后再扩容?
在数据结构接近其容量阈值时,性能可能会开始下降。对于哈希表而言,这可能表现为更多的哈希冲突和更长的查找时间。对于动态数组,接近容量限制可能导致频繁的内存重新分配。通过在达到较低阈值时提前扩容,可以减少这些操作的性能影响,从而“避免滞后”。

  1. 内部有一个Entry静态内部类(键值对实体的存储结构),继承WeakReference

image.png

当一个 ThreadLocal 对象被垃圾回收器回收时,由于 ThreadLocalMap.Entry 对 ThreadLocal 对象的引用是通过弱引用实现的,弱引用所指向的 ThreadLocal 对象确实可以被回收,这将使得 Entry 中的键(key)变为 null。然而,这个过程不会自动将 Entry 中的值(value)设置为 null。
在 ThreadLocalMap 的内部逻辑中,只有当对 ThreadLocalMap 进行操作(机制是懒惰的,只有调用 get()、set() 或 remove() 方法调用)时,相关的清理操作(例如 expungeStaleEntries())才会被触发。这些清理操作会检查键(key)是否为 null,如果是,则会清理掉这些 Entry,包括其中的值(value)。在清理操作之前,这些值(value)仍然占用内存,尽管它们的 ThreadLocal 引用已经被回收。
关键:键是对 ThreadLocal 对象的弱引用,value是被 ThreadLocalMap 的 Entry 以强引用的形式存储的。如果不手动操作,value不会被垃圾回收器回收。

概念补充

理想位置:指该ThreadLocal对象初次计算出的哈希值
错位:哈希值会出现冲突,造成“错位”元素的出现

四种引用级别:

  1. 强引用(Strong Reference)
    特点:强引用是最普遍的引用类型。如果一个对象具有强引用,垃圾收集器绝不会回收它。当内存空间不足时,Java 运行时宁愿抛出 OutOfMemoryError,也不会回收这种对象。
    用途:日常编程中默认使用的引用类型。
    示例:Object obj = new Object(); 这里的 obj 就是一个对 Object 实例的强引用。
  2. 软引用(Soft Reference)
    特点:软引用是用来描述一些还有用但非必需的对象。在系统将要发生内存溢出之前,将会把这些对象列进回收范围进行二次回收。如果回收后内存还是不足,才会抛出内存溢出异常。
    用途:适合用于实现内存敏感的缓存。
    示例:SoftReference softReference = new SoftReference<>(new Object());
  3. 弱引用(Weak Reference)
    特点:弱引用也是用来描述非必需对象的,但是它的强度比软引用更弱一些。被弱引用关联的对象只能生存到下一次垃圾收集发生之前。当垃圾收集器工作时,无论当前内存空间足够与否,都会回收只被弱引用关联的对象。
    用途:弱引用同样适合于实现缓存,也用于 ThreadLocal 来避免内存泄漏。
    示例:WeakReference weakReference = new WeakReference<>(new Object());
  4. 虚引用(Phantom Reference)
    特点:虚引用是所有引用类型中最弱的一个。一个对象是否有虚引用的存在,完全不会对其生存时间构成影响,也无法通过虚引用来获取一个对象实例。唯一的用途是这个对象被收集器回收时收到一个系统通知。
    用途:虚引用主要用来跟踪对象被垃圾回收的活动。
    示例:PhantomReference phantomReference = new PhantomReference<>(new Object(), referenceQueue); 其中 referenceQueue 是在对象被垃圾回收时接收通知的队列。

标签:ThreadLocalMap,对象,回收,ThreadLocal,源码,引用,哈希,解析
From: https://blog.csdn.net/qq_29528917/article/details/137290965

相关文章

  • 【附源码】JAVA计算机毕业设计智慧点餐系统(springboot+mysql+开题+论文)
    本系统(程序+源码)带文档lw万字以上 文末可获取一份本项目的java源码和数据库参考。系统程序文件列表开题报告内容研究背景随着信息技术的快速发展和互联网的普及,人们的生活方式发生了深刻的变化。特别是在餐饮行业,传统的点餐方式已经无法满足现代消费者对于便捷性、个性化......
  • java计算机毕业设计(附源码)医院新型冠状病毒疫苗接种管理系统(ssm+mysql+maven+LW文档)
    本系统(程序+源码)带文档lw万字以上  文末可领取本课题的JAVA源码参考系统程序文件列表系统的选题背景和意义在当今全球疫情的背景下,新型冠状病毒疫苗的接种成为了防控疫情的重要手段。然而,由于疫苗接种人群广泛,且接种过程复杂,需要记录的信息量大,因此,传统的人工管理方式已......
  • java计算机毕业设计(附源码)医院薪酬管理系统(ssm+mysql+maven+LW文档)
    本系统(程序+源码)带文档lw万字以上  文末可领取本课题的JAVA源码参考系统程序文件列表系统的选题背景和意义选题背景:在现代医疗体系中,医院作为提供专业医疗服务的核心机构,其运营效率和服务质量直接影响着公众健康和社会福祉。医院薪酬管理系统是确保医疗人员得到合理报酬......
  • java计算机毕业设计(附源码)医院药品管理系统(ssm+mysql+maven+LW文档)
    本系统(程序+源码)带文档lw万字以上  文末可领取本课题的JAVA源码参考系统程序文件列表系统的选题背景和意义在当今社会,随着医疗技术的不断发展和人们健康意识的提高,医院药品管理系统的重要性日益凸显。药品管理作为医疗服务的核心环节之一,对于确保患者用药安全、提高医疗......
  • java计算机毕业设计(附源码)医院医疗救助系统(ssm+mysql+maven+LW文档)
    本系统(程序+源码)带文档lw万字以上  文末可领取本课题的JAVA源码参考系统程序文件列表系统的选题背景和意义选题背景:随着社会的发展和人口老龄化的加剧,医疗救助系统在现代社会中扮演着越来越重要的角色。医院作为医疗救助的主要场所,其系统的完善与否直接关系到广大人民群......
  • mysql配置文件解析
     mysql服务启动默认使用的配置文件路径mysqld--verbose--help|grepcnfmy.cnf配置文件字段解析[client]port=3306socket=/tmp/mysql.sock[mysqld]port=3306socket=/tmp/mysql.sockbasedir=/usr/local/mysqldatadir=/data/mysqlpid-file=/data/mys......
  • C#/BS手麻系统源码 手术麻醉管理系统源码 商业项目源码
    C#/BS手麻系统源码手术麻醉管理系统源码商业项目源码手麻系统从麻醉医生实际工作环境和流程需求方面设计,与HIS,LIS,PACS,EMR无缝连接,方便查看患者的信息;实现术前、术中、术后手术麻醉信息全记录;减少麻醉医师在手术中填写麻醉记录单时间,证手术麻醉相关信息的准确性,有效降低医......
  • [附源码]JAVA计算机毕业设计电子市场计算机配件报价系统(源码+开题)
    本系统(程序+源码)带文档lw万字以上 文末可获取一份本项目的java源码和数据库参考。系统程序文件列表开题报告内容研究背景随着信息技术的快速发展和普及,计算机作为现代人日常生活和工作中的重要工具,其配件市场的需求日益增长。电子市场作为连接供应商与消费者的桥梁,在推动......
  • [附源码]JAVA计算机毕业设计电子商城购物系统(源码+开题)
    本系统(程序+源码)带文档lw万字以上 文末可获取一份本项目的java源码和数据库参考。系统程序文件列表开题报告内容研究背景随着互联网技术的迅猛发展和普及,网络购物已成为现代人生活中不可或缺的一部分。电子商城购物系统作为网络购物的重要载体,为企业提供了一个全新的销售......
  • 【附源码】计算机毕业设计音乐豆瓣(java+springboot+mysql+mybatis+论文)
    本系统(程序+源码)带文档lw万字以上  文末可领取本课题的JAVA源码参考系统程序文件列表系统的选题背景和意义音乐豆瓣是一个以音乐为主题的社交网站,用户可以在网站上分享自己喜欢的音乐、评论和推荐音乐作品,还可以与其他用户进行交流和互动。音乐豆瓣的目的是为了让更多的......