ThreadLocal通过中文解释就是线程本地变量,是线程的一个局部变量。根据哲学家黑格尔“的存在即合理”的说法,ThreadLocal的出现肯定是有它的意义,它的出现也是因为多线程的一个产物。ThreadLocal既然跟线程有关系,那肯定得先对线程了解了解。

从网上找来了一句话:Java线程的创建,除了堆栈空间,每个线程还需要为线程本地存储(thread-local storage)和内部数据结构提供一些本机内存。

先来学习一下什么是堆栈空间

以上是Java虚拟机运行时数据区的结构图,从图中看出,堆栈(即图中的虚拟机栈)是Java运行时内存分配的一部分,这个堆栈的大小可以用过JVM启动参数Xss设置(JDK5+版本默认好像是1M),那么,这个堆栈是干什么用的呢?大学期间有认真学习过一些技术课程如操作系统、数据结构、C语言等学科的话,不在话下。可惜,我不是这种学生。为了能理解堆栈的一些相关知识,我快速阅览相关知识继续学习(现在才知道大学的知识真的是很用,如果再给我4年时间,算了,现在学习也为时不晚)。一句话,它是线程执行方法(字节码)的地方,每创建一个线程实例,就是分配固定大小(Xss设置参数)的内存空间给线程执行方法用,具体结构图如下:

上图的每一个栈帧就相当于一个方法的执行,更多可参考《深入理解Java虚拟机》8.2章节。

上面已经大概的了解了一下堆栈,那就再来看看线程的堆栈与本地变量的一个关系结构图:

我们知道,线程实例也是一个对象,对象都是存放在堆里面的。从上图可以看出,当创建一个新的线程,那么就会有一个相对应的堆栈空间创建,那个stack部分就可以很好的解析上文提到的一句话“Java线程的创建,除了堆栈空间,每个线程还需要为线程本地存储(thread-local storage)和内部数据结构提供一些本机内存”。这个stack区域就是堆栈空间,而在这个堆栈空间里面有两个直线了堆栈对象的引用,一个是线程实例的应用,另一个就是本地变量的引用。

总结:

1、  堆栈的溢出不会直接因为ThreadLocal保存对象的过大的导致堆栈溢出,因为线程堆栈保存的只是引用。真正的对象还是在堆里面,如果对象大到超出堆内存的限制,反而会导致堆溢出。

2、  从源码可以看出,每个Thread中都存在一个Map,Map的类型是ThreadLocal.ThreadLocalMap。Map中的key为一个Threadlocal实例。这个Map的确使用了弱引用,不过弱引用只是针对key。每个key都弱引用指向Threadlocal。 当把Threadlocal实例置为null以后,没有任何强引用指向Threadlocal实例,所以Threadlocal将会被gc回收。但是,我们的value却不能回收,因为存在一条从current thread连接过来的强引用。只有当前thread结束以后, current thread就不会存在栈中,强引用断开,Current Thread、 Map,、value将全部被GC回收。

3、  堆栈的生命周期是跟随着线程的生命周期,当线程池中的线程实例还在,堆栈也不会被回收或者清空,所以,原来的ThreadLocalMap还是存在的。所以,当线程池与ThreadLocal同时使用的时候特别需要注意。

【Java】ThreadLocal细节分析的更多相关文章

  1. Java ThreadLocal 源代码分析

    Java ThreadLocal 之前在写SSM项目的时候使用过一个叫PageHelper的插件 可以自动完成分页而不用手动写SQL limit 用起来大概是这样的 最开始的时候觉得很困惑,因为直接使 ...

  2. java基础解析系列(七)---ThreadLocal原理分析

    java基础解析系列(七)---ThreadLocal原理分析 目录 java基础解析系列(一)---String.StringBuffer.StringBuilder java基础解析系列(二)-- ...

  3. Java文件读写分析

    本文内容:IO流操作文件的细节分析:分析各种操作文件的方式. 读写一个文件 从一个示例开始分析,如何操作文件: /** * 向一个文件中写入数据 * @throws IOException */ pr ...

  4. 常用 Java 静态代码分析工具的分析与比较

    常用 Java 静态代码分析工具的分析与比较 简介: 本文首先介绍了静态代码分析的基 本概念及主要技术,随后分别介绍了现有 4 种主流 Java 静态代码分析工具 (Checkstyle,FindBu ...

  5. Java线程问题分析定位

    Java线程问题分析定位 分析步骤: 1.使用top命令查看系统资源占用情况,发现Java进程占用大量CPU资源,PID为11572: 2.显示进程详细列表命令:ps -mp 11572 -o THR ...

  6. Java提高篇(三五)-----Java集合细节(一):请为集合指定初始容量

    集合是我们在Java编程中使用非常广泛的,它就像大海,海纳百川,像万能容器,盛装万物,而且这个大海,万能容器还可以无限变大(如果条件允许).当这个海.容器的量变得非常大的时候,它的初始容量就会显得很重 ...

  7. java内存溢出分析(二)

    我们继续java内存溢出分析(一)的分析,点击Details>按钮,显示如下图,我们发现有一个对象数量达到280370216个,再点击其中的List objects 点击后,显示下图 至此,我们 ...

  8. 性能分析之-- JAVA Thread Dump 分析综述

    性能分析之-- JAVA Thread Dump 分析综述       一.Thread Dump介绍 1.1什么是Thread Dump? Thread Dump是非常有用的诊断Java应用问题的工 ...

  9. java初学的分析

    java初学的分析第一阶段:入门阶段学习目标:简单项目开发学习内容:1.Java入门书籍,Java基础知识.关于Java入门级的书,给大家推荐过<Java编程思想>.<Java核心技 ...

随机推荐

  1. 内核对TCP REUSEPORT的优化

    Q&A 当有人问起我关于reuseport的一些事的时候,我们的对话基本如下:Q1:什么是reuseport?A1:reuseport是一种套接字复用机制,它允许你将多个套接字bind在同一个 ...

  2. io流(详询请加qq:2085920154)

    import java.io.File; import java.io.FileInputStream; import java.io.IOException; public class ioTest ...

  3. iis 500.19错误解决过程记录

    前段时间一直在纠结C#中,dll的管理问题.最后选择使用nugetgallery进行公共库管理.项目地址:https://github.com/NuGet/NuGetGallery.这是一个nuget ...

  4. JS中this关键字详解

    本文主要解释在JS里面this关键字的指向问题(在浏览器环境下). 阅读此文章,还需要心平气和的阅读完,相信一定会有所收获,我也会不定期的发布,分享一些文章,共同学习 首先,必须搞清楚在JS里面,函数 ...

  5. html5 canvas绘画时钟

    本示例使用HTML5 canvas,模拟显示了一个时钟, 请使用支持HTML5的浏览器预览效果: HTML部分: <!DOCTYPE html> <html lang="e ...

  6. easyui tree onloadsuccess事件的心得

    在onloadSuccess事件中不能apeed新节点,否则又会触发noloadsuccess事件,形成死循环. 公司电话:028-87657875           13060063607 淘宝店 ...

  7. js 有用的代码

    1. 如何创建嵌套的过滤器: //允许你减少集合中的匹配元素的过滤器, //只剩下那些与给定的选择器匹配的部分.在这种情况下, //查询删除了任何没(:not)有(:has) //包含class为“s ...

  8. 年月日 生日 js插件

    <script typet="text/javascript" src="http://libs.baidu.com/jquery/1.9.1/jquery.min ...

  9. C++内存分配及变长数组的动态分配

    //------------------------------------------------------------------------------------------------ 第 ...

  10. Win7 64位 VS2015及MinGW环境编译FFMPEG-20160326

    因为又要弄MinGW了,所以顺便把FFMPEG编译了,文章主要参考这篇,防抽所以复制一遍,顺便加些自己的内容 http://blog.csdn.net/finewind/article/details ...