ThreadLocal刨根问底
一、ThreadLocal使用场景
数据库连接connection对象使用,每个客户都能使用自己的connection对象。不会出现客户A操作关闭了客户B的connection
案例:https://zhuanlan.zhihu.com/p/82737256
二、ThreadLocal中的remove()使用
1,内存泄露
2,在ThreadLocal和线程池联合使用的时候,下个业务请求复用到这个线程的时候,也会用线程的ThreadLocal里面的变量执行业务逻辑。
三、为什么会出现内存泄露?
四、为什么使用弱引用?
从表面上看,发生内存泄漏,是因为Key使用了弱引用类型。但其实是因为整个Entry的key为null后,没有主动清除value导致。为什么使用弱引用而不是强引用?
官方文档的说法:
To help deal with very large and long-lived usages, the hash table entries use WeakReferences for keys.
为了处理非常大和生命周期非常长的线程,哈希表使用弱引用作为 key。
下面我们分两种情况讨论:
key 使用强引用:引用的ThreadLocal的对象被回收了,但是ThreadLocalMap还持有ThreadLocal的强引用,如果没有手动删除,ThreadLocal不会被回收,导致Entry内存泄漏。
key 使用弱引用:引用的ThreadLocal的对象被回收了,由于ThreadLocalMap持有ThreadLocal的弱引用,即使没有手动删除,ThreadLocal也会被回收。value在下一次ThreadLocalMap调用set,get,remove的时候会被清除。
比较两种情况,我们可以发现:由于ThreadLocalMap的生命周期跟Thread一样长,如果都没有手动删除对应key,都会导致内存泄漏,但是使用弱引用可以多一层保障:弱引用ThreadLocal不会内存泄漏,对应的value在下一次ThreadLocalMap调用set,get,remove的时候会被清除。
因此,ThreadLocal内存泄漏的根源是:由于ThreadLocalMap的生命周期跟Thread一样长,如果没有手动删除对应key的value就会导致内存泄漏,而不是因为弱引用。
ThreadLocal刨根问底的更多相关文章
- 证明:ThreadLocal的get,set方法无法防止内存泄漏
先给出结论:get,set两个方法都不能完全防止内存泄漏,还是每次用完ThreadLocal都勤奋的remove一下靠谱. 前言: 看到有的博客说在把ThreadLocal的所有强引用置空前,调用 ...
- ThreadLocal简单理解
在java开源项目的代码中看到一个类里ThreadLocal的属性: private static ThreadLocal<Boolean> clientMode = new Thread ...
- CSS十问——好奇心+刨根问底=CSSer
最近有时间,想把酝酿的几篇博客都写出来,今天前端小学生带着10个问题,跟大家分享一下学习CSS的一些体会,我觉得想学好CSS,必须保持一颗好奇心和刨根问底的劲头,而不是复制粘贴,得过且过.本人能力有限 ...
- Android线程管理之ThreadLocal理解及应用场景
前言: 最近在学习总结Android的动画效果,当学到Android属性动画的时候大致看了下源代码,里面的AnimationHandler存取使用了ThreadLocal,激起了我很大的好奇心以及兴趣 ...
- Threadlocal使用Case
Threadlocal能够为每个线程分配一份单独的副本,使的线程与线程之间能够独立的访问各自副本.Threadlocal 内部维护一个Map,key为线程的名字,value为对应操作的副本. /** ...
- 多线程映射工具——ThreadLocal
ThreadLocal相当于一个Map<Thread, T>,各线程使用自己的线程对象Thread.currentThread()作为键存取数据,但ThreadLocal实际上是一个包装了 ...
- ThreadLocal 工作原理、部分源码分析
1.大概去哪里看 ThreadLocal 其根本实现方法,是在Thread里面,有一个ThreadLocal.ThreadLocalMap属性 ThreadLocal.ThreadLocalMap t ...
- ThreadLocal<T>的是否有设计问题
一.吐槽 ThreadLocal<T>明显是.NET从JAVA中来的一个概念,但是这种设计是否出现了问题. 很明显,在JAVA中threadLocal直接是Thread的成员,当然随着th ...
- 理解ThreadLocal —— 一个map的key
作用: 当工作于多线程中的对象使用ThreadLocal维护变量时,threadLocal为每个使用该变量的线程分配一个独立的变量副本. 接口方法: protected T initialValue( ...
随机推荐
- keepalived 热备
概述 keepalived高可用集群 keepalived最初是为了LVS的,因为LVS无法进行自动检测服务器的节点状态(可以自动部署LVS) keeplived后来加入VRRP给功 ...
- Pop!_OS配置JAVA环境
Pop!_OS配置JAVA环境 #0x0 安装vscode #0x1 安装JDK #0x2 配置vscode #0x3 安装Eclipse #0x0 安装vscode 见Pop!_OS下安装C++编程 ...
- 方正璞华Java面试总结(武汉)
方正璞华Java面试总结(武汉) 现在社会急缺复合型人才,计算机与日语的结合,具备这两种能力的人不愁工作,最后他们大多到的也是日企,甚至到日本去工作.至今为止接触的日企有光庭.方正璞华.先锋·商泰.英 ...
- Ubuntu systemctl 查看管理系统启动项
Ubuntu systemctl 查看系统启动项 列出所有启动项: sudo systemctl list-unit-files 会列出开启的和未开启的: 使用grep过滤一下开启的grep enab ...
- Scala 基础(五):Scala变量 (二) 数据类型
1 scala数据类型介绍 Scala 与 Java有着相同的数据类型,在Scala中数据类型都是对象,也就是说scala没有java中的原生类型 Scala数据类型分为两大类 AnyVal(值类型) ...
- python面试题五:Python 编程
1.B Tree和B+ Tree的区别? 1.B树中同一键值不会出现多次,并且有可能出现在叶结点,也有可能出现在非叶结点中. 而B+树的键一定会出现在叶结点中,并有可能在非叶结点中重复出现,以维持B+ ...
- redis(二十三):Redis 集群(proxy 型)二
redis的确是一个非常高效的缓存服务器,但是单台redis服务器的内存管理能力有限,如果一味的加大内存的话会导致redis服务器的性能下降,所以就必须要搭建redis集群来提供服务.在redis官方 ...
- CSS背景处理
CSS背景处理 背景样式 背景颜色 如果想让一个区域具有纯色的背景,可以使用background-color进行设置,背景颜色可以是rgb,rgba,#16网页色. <!DOCTYPE html ...
- ffmpeg常见用法总结
1. 视频/音频剪切: ffmpeg -i input_file [-ss 00:00:10] [-t 00:00:20] output_file 去掉-ss指令表示从头开始 去掉-t指令表示剪切到结 ...
- 各种jar包下载地址
standard.jar和jstl.jar的下载地址 http://repo2.maven.org/maven2/javax/servlet/jstl/ http://repo2.maven.org/ ...