用一个例子来解释ThreadLocal
ThreadLocal叫线程本地变量,他为每个线程都创建了一个副本变量,每个线程都只能访问自己的副本变量。
我们直接用一个例子来解释ThreadLocal。
class Message{private String note;public void setNote(String note) {this.note = note;}public String getNote() {return note;}
}
class MessageConsumer{public void print(){System.out.println(Thread.currentThread().getName() + "..." + Test20.msg.getNote());}
}public class Test20 {public static Message msg;public static void main(String[] args) {new Thread(() -> {Message msg = new Message();msg.setNote("你好啊");Test20.msg = msg;new MessageConsumer().print();}, "用户A").start();new Thread(() -> {Message msg = new Message();msg.setNote("Hello");Test20.msg = msg;new MessageConsumer().print();}, "用户B").start();}}
首先我们有一个Message类,提供信息的读写,还有一个信息的打印类MessageConsumer,然后再客户端创建两个线程,这里有一个Message类型的成员,用它来作为全局数据区,减少引用的传递。接下来我们来看看这样做的后果是什么:
执行三次,得到三个结果,而且两个线程打印出来的结果竟都是一样的,这就是变量没有同步的问题,我们来分析一下这个原因:两个或多个线程分别设置了Message信息,这里有一个全局数据区msg,这是线程共享的,用户A线程设置了信息,还没等它打印出来,用户B线程又设置了这个msg,导致后面的线程把前面的线程覆盖了,所以才会出现结果都相同的情况。这时就需要用ThreadLocal来设置一个线程本地变量,每个线程只能操作它自己的副本变量。代码如下:
class Message{private String note;public void setNote(String note) {this.note = note;}public String getNote() {return note;}
}
class MessageConsumer{public void print(){System.out.println(Thread.currentThread().getName() + "..." + MyUtil.get().getNote());}
}
class MyUtil{public static ThreadLocal<Message> threadlocal = new ThreadLocal<>();public static void set(Message msg){threadlocal.set(msg);}public static Message get(){return threadlocal.get();}
}
public class Test20 {public static void main(String[] args) {new Thread(() -> {Message msg = new Message();msg.setNote("你好啊");MyUtil.set(msg);new MessageConsumer().print();}, "用户A").start();new Thread(() -> {Message msg = new Message();msg.setNote("Hello");MyUtil.set(msg);new MessageConsumer().print();}, "用户B").start();}}
再来看一下结果:
这样就实现了变量同步,每个线程只改变自己的数据。
用一个例子来解释ThreadLocal相关推荐
- [机器学习]一个例子完美解释朴素贝叶斯分类器
何为"朴素":属性条件独立性假设 如果已知条件不止一个属性,二是多个呢,这个时候贝叶斯公式可以写作 上述公式假设特征属性 a1,a2⋯ 相互独立,这也是"朴素" ...
- 什么是量子计算机?用一个简单例子来解释
译者:王亮 作者:YK Sugi 原文:http://t.cn/EZAElk0 Hi,大家好! 不久前,我参观了加拿大温哥华的D-Wave Systems公司,这是一家制造前沿量子计算机的公司. ...
- java seda_Java seda,vm和direct之间有什么区别用camel解释它用一个例子
我曾与seda合作并直接和我一起阅读文档.仍然无法想象seda的使用和直接. vm对我来说是新的.请用一个例子解释一下. 至少有四种不同的机制,一种Camel路由可以直接将数据传递给另一种. &quo ...
- Java 堆内存泄漏分析的一个例子
Java 程序开发者,多多少少都遇到过 Java 堆内存溢出的错误,错误发生时可以在日志文件中看到 java.lang.OutOfMemoryError: Java heap space 字样.不像 ...
- python中self_一个例子带你入门Python装饰器
============ 欢迎关注我的公众号:早起python ============ 前言 在还未正式发布的python3.9中,有一个新功能值得关注,那就是任意表达式可以作为装饰器,如果你还不知 ...
- Flutter 初学者的简单例子充分解释
Flutter 初学者的简单例子充分解释 大家好,我是坚果,我的公众号"坚果前端", 关于 Flutter 语言: Flutter 是一种语言工具,允许您使用单一的原生编程语言代码 ...
- 一个例子带你搞懂python作用域中的global、nonlocal和local
在编程中,只要接触过函数的,我相信都理解什么是全局变量和局部变量,概念比较简单,这里就不做解释了.在python中,用global语句就能将变量定义为全局变量,但是最近又发现有个nonlocal,一时 ...
- SDN精华问答 | 使用SDN的一个例子
SDN火热了好一阵子,无论运营商.政府企业.投资机构,一段时间,不知道SDN.不能甩几个SDN相关的名词术语,似乎都落后于时代了.今天,就来看看关于SDN的精华问答吧. 1 Q:为什么会出现SDN呢? ...
- Webpack入门——使用Webpack打包Angular项目的一个例子
(一)什么是Webpack Webpack是一个前端的模块管理工具(module bundler),以下是webpack的官网:http://webpack.github.io/,一进入官网可以看到下 ...
最新文章
- Android:手把手教你 实现Activity 与 Fragment 相互通信(含Demo)
- 重新配对_郑思维和陈清晨当年配对也很强,为什么被拆开重新和黄雅琼配对
- while和for循环读取大文件三种读取文件方式
- python实现监控增量_Python 快速计算增量的方法
- Nginx静态资源压缩实战内容介绍
- js中怎么写自执行函数
- java内存泄漏和内存溢出_Java和内存泄漏
- 比较两大虚拟桌面厂商的系统镜像管理
- php集成环境还需要mysql吗_是选择php集成环境好还是分开安装的原生版好
- 分布式存储绝不简单 —— UCan下午茶-武汉站纪实
- Bailian3709 2进制转化为3进制【进制】
- 计算机并口优点,并口光驱优缺点有哪些 并口光驱如何转串口
- 嵌入式FTP服务器的移植与配置:VSF…
- html5 mediarecorder,用浏览器轻松录制音频、视频—— MediaRecorder API
- Proptech崛起,房地产产业数智化,成了2020年的新风口
- 【工艺】 CNC(数控机床)加工工艺
- 可视化丨用数据分析福尔摩斯探案集
- Dockerfile配置APM监控实现Java容器的性能监控
- R语言并行计算实战教程
- 华为智慧屏 鸿蒙UI 适配荣耀,鸿蒙OS首秀 荣耀智慧屏发布,仅3799元起