Java内存模型JMM
1.JMM介绍:
Java内存模型规定了所有的变量都存储在主内存(Main Memory)中,每条线程还有自己的工作内存(Working Memory),
线程的工作内存中保存了被该线程使用的变量的主内存副本,线程对变量的所有操作(读取、赋值等)都必须在工作内存中进行,而不能直接读写主内存中的数据。
不同的线程之间也无法直接访问对方工作内存中的变量,线程间变量值的传递均需要通过主内存来完成。
下图描述了线程、主内存、工作内存三者的交互关系:
package com.fll.jvm;
public class JMM_Test01 {
public static void main(String[] args) {
Number n = new Number();
//开启A线程
new Thread(()->{
System.out.println(Thread.currentThread().getName()+"开始修改: "+n.number);
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
e.printStackTrace();
}
n.addTo1000(); //将number修改成1000
System.out.println(Thread.currentThread().getName()+"已经修改好了: "+n.number);
},"线程A") .start();
//main线程
while(n.number == 10) {
//需要有一种通知机制告诉main线程,number被修改了
}
System.out.println(Thread.currentThread().getName()+":number: "+n.number);
}
}
class Number{
int number = 10;
//加上volatile之后可以增加可见性
// volatile int number = 10;
public void addTo1000() {
this.number = 1000;
}
}
执行的输出如下图:
现象:main线程一直在等待,说明main线程中的变量没有被修改。直接说明A线程修改了工作内存中的number 并上传至主内存,但是main线程也有一份之前一样的工作副本,如果不通知main线程,那么main线程将一直等下去。
但是如果将number 用volatile修饰,程序会立马结束。
volatile解析
volatile关键字是Java虚拟机提供的最轻量级的同步机制。
具备以下两个特性:
- volatile修饰的变量在多线程中保证了可见性。
- volatile修饰的变量能禁止指令重排序优化。
但是并不能保证原子性...
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· Ollama——大语言模型本地部署的极速利器
· 使用C#创建一个MCP客户端
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· ollama系列1:轻松3步本地部署deepseek,普通电脑可用
· 按钮权限的设计及实现