Java 线程局部存储

Java的线程存储和线程局部变量:讲解Java的ThreadLocal类,并在何时何地应用它 什么是Java的ThreadLocal类 对ThreadLocal的简介及其设计目的 什么是线程存储和线程局部变量 解释线程存储和线程局部变量的概念 解释为什么我们需要线程局部变量 如何使用ThreadLocal 示范ThreadLocal类的API:如何创建ThreadLocal变量、设置变量的值、获取变量的值以及删除变量的值 对上述API调用的结果进行展示 ThreadLocal的适用场景 解释在并发编程中,什么情况下需要ThreadLocal 举例说明在这些场景中如何正确使用ThreadLocal 阅读详情

一,简介和应用

Java中对线程局部存储进行支持的类是:

public class ThreadLocal<T> extends Object

其文档解释为:

该类提供了线程局部 (thread-local) 变量。这些变量不同于它们的普通对应物,因为访问某个变量(通过其 get 或 set 方法)的每个线程都有自己的局部变量,它独立于变量的初始化副本。ThreadLocal 实例通常是类中的 private static 字段,它们希望将状态与某一个线程(例如,用户 ID 或事务 ID)相关联。

解释下这段话:

  1,该类提供“线程局部存储技术”。即尽管表面上,访问的都是这个类的get()方法和set()方法,但是不同的线程设置的和获取的数据是不同的。

  2,该类往往是作为其他类的private static字段存在,用以保持一个与线程本身有关的变量的。


方法摘要
 Tget()
          返回此线程局部变量的当前线程副本中的值。
protected  TinitialValue()
          返回此线程局部变量的当前线程的“初始值”。
 voidremove()
          移除此线程局部变量当前线程的值。
 voidset(T value)
          将此线程局部变量的当前线程副本中的值设置为指定值。

例如,任务类Task被作为线程池的任务执行,线程池的线程执行任务需要统计执行的线程数,因此,这个数可以作为线程局部存储的数据。


public class Task implements Runnable{


    private static final ThreadLocal threadLocal = new ThreadLocal();

    public void run() {

        Integer in = (Integer)threadLocal.get();

        if(in == null){
            //线程里没有该数据,说明是第一次执行
            threadLocal.set(new Integer(1));

        }else{
            //线程中有该数据,则应该进行更新
            threadLocal.set(in+1);

        }

        //执行任务的时候打印下目前已经有多少任务是由该线程执行的

        System.out.println(threadLocal.get().toString()+"  tasks are run by this thread. ");

   }

}


二,实现原理

  这种机制的实现其实很简单。类ThreadLocal中有个内部类ThreadLocalMap 其是 ThreadLocal 和 所设定的值的Key-Value键值对。 例如对于上述例子,第一次则对应的为 threadLocal -- Integer(1)。但是该ThreadLocalMap的实例,则存储于线程中,是线程类的成员变量。

 因此

  1.   public T get() {  
  2.         Thread t = Thread.currentThread();  
  3.         ThreadLocalMap map = getMap(t);  
  4.         if (map != null)  
  5.             return (T)map.get(this);  
  6.   
  7.         // Maps are constructed lazily.  if the map for this thread  
  8.         // doesn't exist, create it, with this ThreadLocal and its  
  9.         // initial value as its only entry.  
  10.         T value = initialValue();  
  11.         createMap(t, value);  
  12.         return value;  
  13.     }
  14.   
  15.  ThreadLocalMap getMap(Thread t) {
  16.         return t.threadLocals;
  17.    }   

如上源代码所示,get()方法先调用getMap(Thread t)方法获取线程的成员变量threadLocals,然后从这个threadLocals中以本ThreadLocal 实例为参数获取其值。

对应的set()方法:

  1.     public void set(T value) {  
  2.         Thread t = Thread.currentThread();  
  3.         ThreadLocalMap map = getMap(t);  
  4.         if (map != null)  
  5.             map.set(this, value);  
  6.         else  
  7.             createMap(t, value);  
  8.     } 
也是从线程中获取其成员变量然后去设置它的(如果没有则创建它,并设置第一个ThreadLocal-值 的映射)。


因此,实际上这个类都是从线程的成员变量中获取自己这个类的实例对应的值的。因此尽管类的参数相同,都是自己,但是不同线程导致数据来源不同,因此设置和获取都是线程自己的成员变量。




线程局部存储的来源?哪些编程语言支持线程局部存储TLS?堆栈? 文章摘要: 本文介绍了线程局部存储(TLS)的概念及其在多线程编程中的重要性,列举了支持TLS的主流编程语言(C/C++、Java/C#/Swift等)。同时探讨了堆栈的起源、地址随机化技术(ASLR)和默认大小设置,比较了不同语言中变量的存储位置差异(如C/C++局部变量在堆栈,Java/C#对象在堆中等)。最后提供了编程技术学习资源和公众号推荐,适合开发者了解底层内存管理和线程安全机制。(149字) 阅读详情

相关推荐

华硕笔记本+Ubuntu 20.04:用cpupower解决Intel CPU频率上不去/功耗墙问题实战

本文详细介绍了在华硕笔记本Ubuntu 20.04系统下使用cpupower工具解决Intel CPU频率受限和功耗墙问题的实战方法。通过禁用Intel P-State驱动、配置userspace模式以及高级调优技巧,帮助用户突破性能瓶颈,提升编译和计算效率。

weixin_42561476的博客 520

java线程局部存储_线程局部存储

线程局部存储线程局部存储(TLS) 是一种存储持续期(storage duration),对象的存储是在线程开始时分配,线程结束时回收,每个线程有该对象自己的实例。这种对象的链接性(linkage)可以是静态的也可是外部的。TLS的一个例子是用全局变量Windows的实现[编辑]每个进程都有一组标志,共TLS_MINIMUM_AVAILABLE(==64)个。每个标志可以被设为FREE或INUS...

weixin_39595164的博客 374

别再到处找了!2024最新银河麒麟V10全版本(飞腾/龙芯/兆芯)官方下载与安装保姆级教程

本文提供2024年银河麒麟V10操作系统全版本(飞腾/龙芯/兆芯)的官方下载与安装保姆级教程,涵盖版本选择、镜像获取、启动盘制作及安装优化等关键步骤,助您高效部署国产操作系统。

weixin_26846533的博客 481

Java-线程局部存储

线程局部存储(thread local storage) TLS会为每一个线程维护一个和该线程绑定的变量的副本,Java平台的java.lang.ThreadLocal是TLS技术的一种实现,解决多线程中的对同一变量的访问冲突的一种技术。 本地存储的作用和数据同步类似,防止多线程同时对某个共享变量的修改导致的混乱,使得每个线程都是在修改自己本地的变量,相互之间没有交集,所以不会有冲突。但是不同于线程内部的局部变量,线程本地变量是在线程外面定义的。 使用ThreadLocal类的 set 和 get .

CAFE-BABE的博客 539

SVPWM分析、各个扇区详细计算以及Matlab仿真

SVPWM分析以及各个扇区详细计算以及Matlab仿真说明目的两电平逆变器拓扑空间矢量扇区判断扇区内如何发波?矢量作用时间计算矢量切换时间的计算Simulink仿真/基于Matlab-R2014a版本 说明 第一次发文章,不太会用Markdown,word编辑的公式复制过来有些是乱码,因此都贴图了。 另外,本文公式和图片比较多,编辑工作量比较大,比较辛苦,转载的话,请注明出处,谢谢。 目的 由于在...

michaelf的博客 12万+

2025华为OD机试真题+全流程解析+备考攻略+面试技巧+机考经验分享+Java/python/JS/C++/C语言实现

本专栏包含华为 OD 机试最新的 A卷+B卷+C卷+D卷+E卷题库,为全网最全、最新题库,500+真题。每一篇文章都包含了题目描述、解题思路以及实现代码。同时免费提供最新的在线OJ 刷题系统。已有上百名小伙伴通过刷真题题库通过了华为od机考,拒绝一切形式的代考,替考行为!!!以下是本专栏详细内容介绍:本专栏提供在线OJ刷题系统:OJ题库OJ系统注册&使用教程:OJ使用教程其他专栏以及答疑介绍:50+ 高频面试手撕真题,已有上百位小伙伴高频认证。1:机试没过,半年的冷冻期。2:已经订阅过我专栏的同学,推荐新人

MISAYAONE的博客 2225

学习Spring必学的Java基础知识(6)----ThreadLocal

[b][size=x-large]引述[/size][/b]要学习Spring框架的技术内幕,必须事先掌握一些基本的Java知识,正所谓“登高必自卑,涉远必自迩”。以下几项Java知识和Spring框架息息相关,不可不学(我将通过一个系列分别介绍这些Java基础知识,希望对大家有所帮助。): [b][color=red] [1] Java反射知识-->Spring IoC :[url]http...

stamen的程序员之路 762

SMART200如何实现多次调用子程序带定时器功能

1、西门子200PLC的子程序由于很多限制条件,如果希望建立一个可以多次调用的子程序,那么这个子程序里是不能含有定时器指令的,所以我们只能退而求其次了。建议将沿指令(上升沿、下降沿)放在多次调用子程序的外面。 2、可以提供不同的时基,提供不同时间的定时 3、实现秒定时 5、子程序内部: STL代码: 1、时基信号由外部提供、 可以提供不同的时基信号 2、实现循环定时开关 LD #Start:L0....

RXXW_Dor的博客 1万+

多线程(46)线程局部存储

线程局部存储(Thread Local Storage, TLS)是一种允许数据在多个线程中被独立地存储的编程范式。在Java中,这通过类实现,它提供了一种线程封闭的机制,确保每个线程都有自己的变量副本,从而避免了变量共享所带来的线程安全问题。

qq_43012298的博客 581

【PCIe 总线及设备入门学习专栏 1.3 -- PCIe 基础知识 lane和link介绍】

PCIe RC(Root Complex)是PCIe树的根节点,一个RC 可以包括多个 RP(Root Port),例如一个16 条 lane的PCIe RC 可以包括4个RP(4个x4的),或者8个RP(8个x2的)等等。在该模式下,数据传送由CPU执行I/O端口指令来按照字节或更大的数据单位来处理,占用大量的CPU资源,数据传输速度也大大低于DMA模式。国内应该有公司做出相应的phy芯片(例如芯动科技、牛芯半导体),毕竟常见的pcie 3.0才8 Gbps的速率,最新的6.0才64Gbps。

CodingCos的博客 2104

华为OD机试真题 新系统【小花获胜的奶茶】

华为OD机试真题 新系统【小花获胜的奶茶】,提供C语言、Java、C++、Python、Go、JavaScript源码实现,并提供完整思路讲解,以及在线OJ模拟做题。华为OD机试真题 【小花获胜的奶茶】多语言题解。

qq_45776114的博客 382

多线程编程中的线程局部存储实践

1.背景介绍 线程局部存储(Thread-Local Storage,TLS)是一种用于在多线程环境中存储和访问特定于线程的数据的机制。它允许每个线程有自己独立的数据存储区域,从而避免了多线程中的数据竞争和同步问题。在这篇文章中,我们将深入探讨线程局部存储的核心概念、算法原理、实现方法和应用场景。 1.1 多线程编程的挑战 在多线程编程中,多个线程可以并行执行,提高程序的执行效率。然而,多线...

AI天才研究院 577

YOLOv5源码逐行超详细注释与解读(5)——配置文件yolov5s.yaml

全网最详细的YOLOv5源码解读之配置文件yaml。逐行注释,逐句讲解,一文带你了解yaml。小白必看!

路人贾的博客 1万+

java 线程局部存储,线程局部存储tls的使用

线程局部存储(Thread Local Storage,TLS)主要用于在多线程中,存储和维护一些线程相关的数据,存储的数据会被关联到当前线程中去,并不需要锁来维护。。因此也没有多线程间资源竞争问题,那如何去实现TLS存储呢,主要有以下几种方式:gcc和clang的__thread修饰符windows下msvc的__declspec(thread)修饰符pthread库pthread_setspe...

weixin_28864139的博客 263

IDEA的使用指南

IDEA基于java的使用手册,可以最快速的上手,在使用中不断的丰富自己的使用技巧.

Devexpress16.2.6破解工具

Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具

java 线程局部存储,C++采用TLS线程局部存储的用法实例

本文实例讲述了C++采用TLS线程局部存储的用法。分享给大家供大家参考。具体方法如下:// useTLS.cpp : 定义控制台应用程序的入口点。//#include "stdafx.h"#include #include //声明VOID InitStartTime();DWORD GetUserTime();//TLS索引,作全局变量DWORD g_dwTlsIndex;VOID InitS...

weixin_39548740的博客 117

Data-Structures-and-Algorithm-Analysis-in-Java.pdf

作者: Weiss, Mark A. 出版社: Addison Wesley Data Structures and Algorithm Analysis in Java is an “advanced algorithms” book that fits between traditional CS2 and Algorithms Analysis courses. In the old ACM Curriculum Guidelines, this course was known as CS7. This text is for readers who want to learn good programming and algorithm analysis skills simultaneously so that they can develop such programs with the maximum amo...

线程局部存储 java_使用线程局部存储实现多线程下的日志系统

多线程环境的日志多线程环境下实现日志系统,必须对写操作加锁,否则将得到混乱的输出。容易想到的方法是:在 Logger 类中维护一个列表,按名字存放所有线程中 Logger 的实例,并在每个线程中按名字查找并使用线程自己的唯一一个 Logger。这跟 log4j 的实现有点像,不同的是 log4j 把所有的 Logger 配置都放在配置文件里,每个 Logger 都有独立的配置。但是我们的 Logg...

weixin_35361584的博客 205

android 蓝牙通讯demo

android 下蓝牙通讯demo,实现了发现蓝牙,使能蓝牙,通过蓝牙发送消息。

java 线程局部存储,线程局部存储空间 pthread_key_t、__thread 即 ThreadLocal

__thread是GCC内置的线程局部存储设施,__thread变量每一个线程有一份独立实体,各个线程的值互不干扰。可以用来修饰那些带有全局性且值可能变,但是各线程独立不干扰的变量;只能修饰POD类型(类似整型指针的标量),不能修饰class类型,因为无法自动调用构造函数和析构函数;可以用于修饰全局变量,函数内的静态变量,不能修饰函数的局部变量或者class的普通成员变量;且__thread变量值...

weixin_34163020的博客 333

java 线程局部存储,转载boost::thread简要分析(3):线程局部存储及其它

多线程编程中还有一个重要的概念:Thread Local Store(TLS,线程局部存储),在boost中,TLS也被称作TSS,Thread Specific Storage。boost::thread库为我们提供了一个接口简单的TLS的面向对象的封装,以下是tss类的接口定义:class tss{public:tss(boost::function1* pcleanup);void* get...

weixin_28894691的博客 197

Java 单例枚举与线程局部存储示例

Java 单例枚举与线程局部存储示例

Leon_Jinhai_Sun的博客 867

java 入门测试代码(spring boot 8) 线程局部存储

线和局部存储实现线程安全 引述要学习Spring框架的技术内幕,必须事先掌握一些基本的Java知识,正所谓“登高必自卑,涉远必自迩”。以下几项Java知识和Spring框架息息相关,不可不学(我将通过一个系列分别介绍这些Java基础知识,希望对大家有所帮助。):[1] Java反射知识-->Spring IoC :http://www.iteye.com/topic/1123081 [...

yangzm的专栏 190

深入理解 ThreadLocal:线程局部存储与内存泄露防范

它为每个线程创建一个副本,确保每个线程只能访问自己的副本,避免了线程间的资源竞争,从而实现线程安全。的内部实现和如何防止内存泄漏,是我们在使用多线程编程时提高性能和避免问题的关键。提供了一种有效的方式来为每个线程存储独立的变量,避免了多线程并发时资源竞争的问题。并不是用来解决共享资源的多线程访问问题的,它的资源并非共享,而是每个线程独享。的核心思想是每个线程都有一个独立的存储空间。是否存在,如果存在就直接更新值,如果不存在,则创建新的。的关系,以及如何避免常见的内存泄漏问题。来存储每个线程的局部变量。

dm菜鸟编程的专栏 1146

Java的知识点集合06:final&访问权限&线程&垃圾回收机制& HttpServletRequest、HttpServletResponse&线程局部存储TLS&接口

访问权限 线程–Thread、Runnable 线程调用start()启动,调用run()运行。run()方法当作普通方法的方式调用。程序还是要顺序执行,要等待run方法体执行完毕后,才可继续执行下面的代码, 这样就没有达到写线程的目的。 垃圾回收机制 垃圾回收主要针对的是堆区的回收,而栈区的内存是随着线程而释放。 堆分成三个区:年轻代(Young Generation)、年老代(Old Gen...

xuxuan1997的博客 588

线程局部存储

线程局部存储(Thread Local Storage,TLS)是一种在多线程编程中非常重要的技术,它允许为每个线程分配独立的存储空间,使得不同线程可以拥有不同的内存区域。这种机制确保了数据的线程独立性,从而避免了全局变量或静态变量在并发环境下的竞态条件和数据不一致问题。线程局部存储的主要优点在于它能够减少线程间的同步开销,因为每个线程都有自己的私有数据副本,不需要通过锁或其他同步机制来访问这些数据。

如无必要,勿增实体。 1279

Java多线程中的线程局部变量共享

本文介绍了Java中实现线程局部变量共享的三种方法:1)使用ConcurrentHashMap以线程为键存储数据;2)扩展为共享包含多个属性的数据对象;3)使用ThreadLocal机制实现线程封闭。每种方法都通过核心代码和示例演示了如何让不同线程访问各自独立的数据副本,避免线程间干扰。ThreadLocal方法最为简洁高效,是Java推荐的线程局部变量实现方式。这些技术在多线程编程中确保数据线程安全性具有重要意义。

qq_52506743的博客 706
上一篇: Java线程池技术之二 Java自带线程池实现
下一篇: Java正则表达式
IterZebra
博客等级 码龄16年 56粉丝 38原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值