Java内存模型与线程规范详解:JMM重排序规则
需积分: 10 59 浏览量
更新于2024-07-17
收藏 323KB PDF 举报
"Java多线程高并发基础篇(六)-JMM重排序规则"
在Java多线程编程中,理解Java内存模型(Java Memory Model,简称JMM)及其重排序规则至关重要。JSR-133是Java TMM(Thread Memory Model)和Thread Specification的一个社区审查草案,旨在成为Java 1.5(Tiger)版本的一部分,并替换Java语言规范第17章和Java虚拟机规范第8章的内容。该文档以通用形式编写,最终会针对Java语言和虚拟机分别提供两个版本,但语义上基本保持一致。
JSR-133的制定过程非常详尽且技术性强,涉及了学术领域的多个深入研究。相关的讨论和发展记录在JMM的官方网站http://www.cs.umd.edu/~pugh/java/memoryModel上,这个网站提供了额外的信息,有助于理解该规范是如何形成的。
JMM的核心语义部分(第4至7节)旨在描述现有JVM允许的语义。现有的Java语言规范和虚拟机规范章节定义了一些允许的语义,这些语义在实际运行时可能会导致数据竞争和可见性问题。例如,由于处理器优化,编译器可能会对指令进行重排序,这可能会影响到多线程环境中的程序执行顺序。
重排序是指编译器或处理器为了优化性能,可能改变程序中指令的执行顺序。在单线程环境下,这种重排序通常不会影响程序的正确性,但在多线程环境中,如果一个线程看到另一个线程中指令的重排序结果,就可能导致预期之外的行为。
JMM规定了以下限制来避免这些问题:
1. ** Happens-Before原则 **:这是判断数据是否可见性的基础。如果一个操作A在操作B之前发生(Happens-Before),那么在所有线程中,操作A的结果对操作B都是可见的。这个原则包括同步语义、 volatile写操作、构造函数完成等场景。
2. ** volatile变量规则 **:volatile变量的读写操作具有特定的内存语义,保证了线程间的数据同步。写操作后其他线程的读操作能看到最新值,且禁止对volatile变量的写操作与其他操作的重排序。
3. ** 锁规则 **:进入同步块或方法(即acquire操作)之前,会清空工作内存,确保读取到共享变量的最新值;退出同步块或方法(即release操作)时,会将工作内存中的更新写回主内存,保证其他线程能看到这些更新。
4. ** 初始值设定符规则 **:每个线程在开始执行时,都会看到初始化的静态变量的值,这是由类加载机制保证的。
5. ** 线程启动、终止、中断和 join 规则 **:这些操作也有相应的Happens-Before关系,确保线程的生命周期事件对其他线程的可见性。
理解并遵循这些规则,开发者可以编写出正确处理并发问题的代码,避免数据不一致和竞态条件。在实际编程中,可以利用synchronized关键字、volatile变量、java.util.concurrent包提供的工具类等手段来实现线程间的同步和通信,保证多线程环境下的正确性。同时,了解JMM的重排序规则有助于编写出高效且可预测的并发程序。
2020-09-04 上传
2021-10-26 上传
2020-04-16 上传
2020-12-21 上传
2010-06-05 上传
2021-08-16 上传
2019-01-23 上传
2019-04-26 上传
2016-09-22 上传
weixin_38669628
- 粉丝: 387
- 资源: 6万+
最新资源
- CSharp算法Cambridge University Press - Data Structures and Algorithms Using C# (Mar 2007)
- 华为_Verilog HDL入门教程
- 基于CAN总线的β-甘露聚糖酶发酵控制系统的研究
- 2009年考研计算机专业基础综合大纲
- altera nios从入门到精通
- 类人机器人手臂控制系统设计
- 单元测试测试用例设计
- Windows文件系统过滤驱动开发教程(第二版)
- 常用485芯片通信协议
- 232-485转接电路
- linux多线程编程手册.pdf
- Tornado使用指南
- x5045简介资料 设计的好帮手
- 《MiniGUI 用户手册》.pdf
- cc2500中文数据手册
- hibernate in action(第二版)