threadlocal内存泄漏的原因

ThreadLocal内存泄漏原因详解 ThreadLocal泄漏的原因详解 阅读详情

ThreadLocal的原理:

ThreadLocal的set实际实在当前线程对象里创建了一个内部变量ThreadLocalMap<ThreadLocal,object> ,ThreadLocalMap的key是ThreadLocal的引用。

造成泄漏的原因:

由于ThreadLocal对象是弱引用,如果外部没有强引用指向它,它就会被GC回收,导致Entry的Key为null

如果当前的情况下在栈中将threadlocal1的引用设置为null,强引用1将会失效,那堆中的threadlocal1对象因为ThreadLocalMap的key对它的引用是弱引用,将会在下一次gc被回收,那就会出现key变成null,如果这时value外部也没有强引用指向它,那么value就永远也访问不到了,按理也应该被GC回收,但是由于ThreadLocalMap.Entry对象还在强引用value,导致value无法被回收,这时「内存泄漏」就发生了,value成了一个永远也无法被访问,但是又无法被回收的对象。

解决办法:

                 1:将ThreadLocal设置为空之前,执行remove()方法,会将key为空的键值对清空

                  2:尽量将ThreadLocal设置成static

                  3: 非必要尽量不要在ThreadLocal中放大对象

ThreadLocal做出的努力

ThreadLocal不是洪水猛兽,不要听到「内存泄漏」就不敢使用它,只要你规范化使用是不会有问题的。再者,就算你不规范使用,ThreadLocal也做出了很多努力来最大程度的帮你避免发生「内存泄漏」。

前面已经说过,由于Key是弱引用,因此ThreadLocal可以通过key.get()==null来判断Key是否已经被回收,如果Key被回收,就说明当前Entry是一个废弃的过期节点,ThreadLocal会自发的将其清理掉。

hreadLocal会在以下过程中清理过期节点:

调用set()方法时,采样清理、全量清理,扩容时还会继续检查。
调用get()方法,没有直接命中,向后环形查找时。
调用remove()时,除了清理当前Entry,还会向后继续清理。

为什么这里要用弱引用:

网上有的文章将ThreadLocal内存泄漏的原因怪罪于Entry的Key的弱引用,这个说法是极其错误的!

不用弱引用就能避免「内存泄漏」了吗?当然不是!!!
恰恰相反,使用弱引用是JDK在尽量避免程序出现「内存泄漏」,如下代码:

public class Test {
    public static void main(String[] args) {
        ThreadLocal threadLocal = new ThreadLocal();
        threadLocal.set(new Object());
        threadLocal = null;
    }
}

创建一个ThreadLocal对象,并设置一个Object对象,然后将其置空。如果Key不是弱引用的话,threadLocal无法被回收,也无法被访问,object无法被回收,也无法被访问,Key和Value同时出现了「内存泄漏」

            

聊一聊ThreadLocal内存泄漏的问题 ThreadLocal你真的懂了吗? 阅读详情

相关推荐

ThreadLocal为什么存在内存泄漏,源码分析

详细介绍ThreadLocal的各种坑,内存泄漏的原因等

qq_1149513559的博客 2255

浅谈ThreadLocal

1. ThreadLocal简介 ThreadLocal叫做线程变量,意思是ThreadLocal中填充的变量属于当前线程,该变量对其他线程而言是隔离的,也就是说该变量是当前线程独有的变量。ThreadLocal为变量在每个线程中都创建了一个副本,那么每个线程可以访问自己内部的副本变量。 ThreadLoal 变量,线程局部变量,同一个 ThreadLocal 所包含的对象,在不同的 Thread 中有不同的副本。这里有几点需要注意: 因为每个 Thread 内有自己的实例副本,且该副本只能由当前 Thr

大家好,我是千楼,全栈开发工程师,分享日常学习和工作,记录成长~~~ 5296

23、ThreadLocal内存泄漏原因,如何避免

ThreadLocal内存泄漏原因,如何避免

weixin_43860634的博客 390

图文Debug详解 ThreadLocal内存泄漏的原因

一、前言 在分析ThreadLocal导致的内存泄露前,需要了解一下内存泄露、强引用与弱引用以及GC回收机制。这样才能更好分析ThreadLocal泄漏的原因。 如果了解上述问题可直接跳到第二节。 1.1 内存泄漏 如果不会被使用的对象或者变量占用的内存不能被回收,就是内存泄漏。如果泄漏的数据量足够大,可能会引起内存溢出,导致程序异常结束。 1.2 强引用与弱引用 强引用: 如 String name = new String(); 一个对象具有强引用,不会被垃圾回收器回收。当内存空间不足,Java虚拟机

qq_40205337的博客 5350

用STM32的SPI接口读取MT6835磁编码器,手把手教你避开数据读取的坑

本文详细介绍了如何使用STM32的SPI接口读取MT6835磁编码器,并提供了21个实战细节与避坑指南。从硬件连接、SPI配置到数据解析和实时调试,全面解析了读取位置信息过程中的常见问题及解决方案,帮助工程师在工业控制、伺服电机等场景中高效应用AMR技术。

weixin_30729609的博客 1439

【阿里云大模型高级工程师ACP习题集】2.7 通过微调增强模型能力 (上篇)(⭐️⭐️⭐️ 重点章节!!!)

【摘要】这是我精心整理出对应的习题集,里面足足有 30 道题目,从基础概念到深度拓展,全方位覆盖章节重点、难点。不管你是想检验自己的学习成果,还是想针对薄弱环节进行强化训练,它都能完美适配!

davidkorhenn的博客 1603

面试官:ThreadLocal 内存泄漏的产生原因以及如何处理

在多线程环境中提供线程局部存储,但如果不正确使用,尤其是在多线程复用的情况下(如线程池),可能导致内存泄漏。为了避免内存泄漏,应该确保在使用完后显式调用remove()方法清理数据,尤其是在处理完请求后,避免在长期存在的线程中保留不必要的数据。博主深知大多数程序员,想要提升技能,往往是自己摸索成长,但自己不成体系的自学效果低效又漫长,而且极易碰到天花板技术停滞不前!因此收集整理了一份《2024年最新JAVA全套学习资料》,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友。

Venus's Blog 8万+

restbed编译笔记

Restbed 可以构建出基于asio库的restfulAPI服务,Restbed 4.7版本使用了1.12.0版本的asio(其他版本编译不通过),可直接访问github下载:https://github.com/chriskohlhoff/asio/tree/asio-1-12-0。另外Restbed还依赖openssl库(可直接下载exe的安装包,安装后取出lib库及头文件放到到restbed\dependency\openssl中即可,https://slproweb.com/download/W.

mahong100的博客 2106

ThreadLocal内存泄漏的原因,如何避免

1、内存泄漏和OOM(内存不足)   内存泄漏:不会被使用的对象或者变量无法被回收;   内存不足:没有剩余的空间可以创建新的对象或者变量。 2、ThreadLocal实现原理   ThreadLocal实现原理:每一个Thread维护一个ThreadLocalMap对象,key为弱引用ThreadLocal对象;value为线程变量的副本。 3、ThreadLocal内存泄漏原因   由于Entry中value是强引用,key为弱引用;当CG回收ThreadLocal后,由于value是强引用,无法被回

weixin_44356698的博客 5685

基于libVLC的视频播放器之四:直接使用libVLC

一.效果 播放本地文件 播放网络url:rtsp://3.84.6.190/vod/mp4:BigBuckBunny_115k.mov 二.实现 既然有VLC-Qt,为什么还要直接调用libVLC呢,因为直接调用会加深对整个播放流程的理解,方便后面修改VLC-Qt源码。 注意事项: 1.编译报错:error C2065: “libvlc_media_read_cb”: 未声明的标识符。修改如下: 2.libvlc_new(0, nullptr)返回null 将plugins

草上爬的博客 5049

我的AI个人公司成立:基于Skills与Qwen大模型的智能问答平台实战开发+龙虾团队

微学AI推出数字员工矩阵,包含10个核心AI角色(总经理、秘书、工程师等),每个角色具备专属技能模块。系统采用FastAPI+Vue3技术栈,核心功能包括:基于SkillLoader的动态技能管理(支持脚本执行和文档加载)、WebSocket流式输出、多轮对话上下文管理。通过模块化架构实现AI自驱协作,可自主完成从需求分析到开发落地的全流程。项目亮点在于声明式技能配置和实时交互能力,打破传统办公壁垒,提升工作效率。

微学AI的博客 1624

ThreadLocal造成内存泄漏的原因

ThreadLocal造成内存泄漏的原因

weixin_39466433的博客 845

【案例讲解】LVGL关于旋转的配置

在实现项目中,因为横竖屏的关系,需要对其做90度的旋转。配置旋转时发现一些局部刷新控件,旋转后效果不对。异常图标正常图标。

Bigan(安)的博客 4284

全面分析!ThreadLocal内存泄漏的原因!

可能大部分的人都会说,是因为弱引用,因为弱引用时,gc会直接内存回收掉,那么引用的值就会为null,这一点其实我一直很困惑,如果弱引用直接内存回收掉,那么存在threadLocal里面的值不就没有了吗?从上面的分析,我们发现内存泄漏的一部分原因是由于,Entry对象的弱引用,但是为什么设置Entry引用的ThreadLocal对象为弱引用呢,其实将他设置成弱引用也是防止内存泄漏的,看到这里,一些读者可定会很困惑,内存泄漏的原因和他有关,但是为什么他却又是防止内存泄漏呢?我们看一下remove方法的实现。

z1ztai的博客 374

GStreamer中h264parse元素

h264parse是 GStreamer 中处理 H.264 视频流的关键元素,主要负责解析和准备 H.264 流以便后续处理。

深之JohnChen的专栏 1022

使用C/C++复制图像

要使用上述代码,需要将输入图像和输出图像的文件名替换为实际的图像文件名。当程序执行完毕后,将会在当前目录下生成一个名为"output.jpg"的图像文件,其中包含与输入图像完全相同的图像数据。要使用上述代码,需要将输入图像和输出图像的文件名替换为实际的图像文件名。当程序执行完毕后,将会在当前目录下生成一个名为"output.jpg"的图像文件,其中包含与输入图像完全相同的图像数据。函数将输出图像保存到文件中。在这个示例中,我们假设输入图像是一个常见的JPEG图像,文件名为"input.jpg"。

CyberWarpX的博客 729

ThreadLocal内存泄漏原因分析,以及如何避免

ThreadLocal内存泄漏原因分析,以及如何避免 内存泄漏是程序在申请内存后,无法释放已申请的内存空间,多次内存泄漏就会导致内存耗光的严重问题。 强引用:使用最普遍的引用(new),一个对象具有强引用,不会被垃圾回收器回收。当内存空间不足,java虚拟机宁愿抛出OutOfMemoryError错误,使程序异常终止,也不回收这种对象。 如果想取消强引用和某个对象之间的关联,可以显式地将引用赋值为null,这样可以使JVM在合适的时间回收该对象。 弱引用:JVM进行垃圾回收时,无论内存是否充足,都会回收被弱

w759826115的博客 4737

汉书HE8,好用的汇编代码编写工具

汉书HE8,好用的汇编代码编写工具早期编写汇编代码所用功能强大

ThreadLocal内存泄漏的真实原因

ThreadLocal内存泄漏的真实原因

乐嘉工作室 378

LinePhone3.2.7(android端最新版本) sip客户端

SIP客户端For android:LinePhone3.2.7(最新版本),官网地址:http://www.linphone.org/

visio安装包

Microsoft Office Visio 是一款专业的制图软件。利用经过更新的形状、协作工具和数据链接图表,创建专业级图表以简化复杂的信息。

ThreadLocal引发内存泄漏的原因及解决方案

【代码】ThreadLocal引发内存泄漏的原因及解决方案。

yuanmomoya的博客 1764

JAVA ThreadLocal内存泄漏原因分析

首先需要了解java中各个引用对应的垃圾回收策略 1.强引用(StrongReference) 强引用是使用最普遍的引用。如果一个对象具有强引用,那垃圾回收器绝不会回收它。当内存空间不足,Java虚拟机宁愿抛出OutOfMemoryError错误,使程序异常终止,也不会靠随意回收具有强引用的对象来解决内存不足的问题。 2.软引用(SoftReference) 如果一个对象只具有软...

mushang8923的博客 1499

经过彻夜研究终于搞懂ThreadLocal内存泄漏的原因了

所以在 ThreadLocal 的内存泄漏问题主要是针对将 ThreadLocal 定义为局部变量的时候,如果不手动 remove 可能会导致 ThreadLocalMap 中的 Entry 对象无法回收,一直占用内存导致内存泄漏,直到当前 Thread 结束之后才会被回收。当然 JDK 的开发者想到了这个问题,在使用 set get remove 的时候,会对 key 为 null 的 value 进行清理,使得程序的稳定性提升。结果:控制台无输出,value没有被回收,发生泄漏。

xmhnl的博客 2401

ThreadLocal的内存泄漏原因与解决方案

在前面的文章中,我们已经掌握了 ThreadLocal 的使用、底层原理以及 ThreadLocalMap 的结构设计。看似简单的 ThreadLocal,却隐藏着一个高频“陷阱”—— 内存泄漏 。不少开发者在使用 ThreadLocal 后,因忽视细节导致应用内存持续飙升,甚至 OOM(内存溢出)。本文将深入拆解 ThreadLocal 内存泄漏的根本原因,理清强引用、弱引用的关键作用,并给出可落地的解决方案和实战避坑要点。

y245166349的专栏 1167

ThreadLocal 内存泄漏原因

ThreadLocal 的 ThreadLocalMap 中 Entry 的 key 是弱引用,value 是强引用。当外部 ThreadLocal 引用置空,GC 回收 key 后,value 还被 Entry 强引用。在线程池线程复用的场景,线程不会销毁,value 对象无法被回收,造成内存泄漏。最佳实践是使用完毕在 finally 块调用 remove。

幽静净土的技术分享 223

一篇文章带你理解ThreadLocal原理和理解内存泄漏的原因

很多人图方便,把定义为静态变量,全局共享。这样会延长实例生命周期,即使线程退出了,它挂的值还在那儿——弱引用还没释放,value 就一直占着内存不放。

2301_81230656的博客 1250

使用ThreadLocal可能导致内存泄漏的原因与其底层实现机制

内存泄漏条件实例被回收 + 线程长期存活 + 未调用remove()。最佳实践始终在finally块中调用remove ()。避免在长生命周期线程中滥用。使用静态实例(减少实例数量,但需更谨慎清理)。通过理解底层机制并遵循最佳实践,可以有效避免的内存泄漏问题。学海无涯,志当存远。燃心砺志,奋进不辍。愿诸君得此鸡汤,如沐春风,事业有成。若觉此言甚善,烦请赐赞一枚,共励学途,同铸辉煌!

qq_40453972的博客 722
上一篇: jvm常用配置
下一篇: mat使用
Oliver486
博客等级 码龄13年 879粉丝 20原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值