一个JIT激进优化引起的可见性误解

本文探讨了在测试Java volatile可见性时出现的误解,指出常见的测试用例实际上验证的是读不到最新值的情况。通过分析JIT编译优化,特别是C2优化后的汇编代码,揭示了JIT的激进优化可能导致的死循环现象。添加打印语句或使用volatile可以避免这种优化,确保每次获取新的值。最后,文章强调在并发环境下,没有同步器保障的可见性测试是复杂的,因为线程执行顺序无法确定。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

背景

这篇文章最开始再我的群里面有讨论过,当时想写的这篇文章的,但是因为一些时间的关系所以便没有写。最近阅读微信文章的时候发现了一篇零度写的一篇文章《分享一道阿里Java并发面试题》,对于有关Java并发性技术的文章我一般还是挺感兴趣的,于是阅读了一下,整体来说还是挺不错的,但是其中犯了一个验证可见性的问题。由于微信文章回复不方便讨论,于是我便把之前一些和群友的讨论在这里写出来。

如何测试可见性问题

因为在群里面我们习惯的有每周一问,也就由我或者群友发现一些由意思的问题然后提问给大家,让大家参与讨论,当时我提出了一个如何测试vlolatile可见性的问题,首先在Effective Java给出了一个测试volatile可见性的例子:

import java.util.concurrent.*;  
  
public class Test {
     
    private static /*volatile*/ boolean stop = false;  
    public static void main(String[] args) throws Exception {
     
        Thread t = new Thread(new Runnable() {
     
            public void run() {
     
                int i = 0;  
                while (!stop) {
     
                    i++;  
//                    System.out.println("hello");  
                }  
            }  
        });  
        t.start();  
  
        Thread.sleep(1000);  
        TimeUnit.SECONDS.sleep(1);  
        System.out.println("Stop Thread");  
        stop = true;  
    }  
}  

这里大家可以复制上面的代码,你会发现这里程序永远不会结束,在零度的那篇文章中也给出了一个测试可见性的例子:

public class 
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值