volatile保证可见性验证

可见性:在多线程的环境下,一个线程对共享变量的修改,其他线程可以看到变量修改后的值。
验证可见性demo:

public class TestVolatile extends Thread {

    volatile boolean flag;

    @Override
    public void run() {
        try {
            Thread.sleep(3000L);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        //子线程停顿3秒后,将flag修改为true
        flag = true;
        System.out.println(Thread.currentThread().getName() + "线程将flag修改为:" + flag);
    }

    public static void main(String[] args) {
        TestVolatile testVolatile = new TestVolatile();
        testVolatile.start();

  //如果flag为false,主线程一直循环判断,直到flag为true,停顿1秒,输出修改以后的flag值
        while (true) {
            if (testVolatile.flag) {
                try {
                    Thread.sleep(1000L);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                System.out.println(Thread.currentThread().getName() + "线程读取到flag被改了");
                break;
            }
        }
    }
}

代码执行结果:
Thread-0线程将flag修改为:true
main线程读取到flag被改了

如果不加volatile关键字,当我们修改flag以后,主线程不会读到修改以后的值,程序会一直处于循环中,为什么会出现这种情况?先看一下下面这张图
在这里插入图片描述
JMM(JAVA内存模型):他说一个抽象的概念,并不真实存在,他描述的是一组规范,通过该规范定义了各个变量的访问方式。
由于JVM运行程序的实体是线程,每个线程在创建时,JVM都会分配一个单独的工作内存,不同线程之间不能访问对方的工作内存呢,线程间通过主内存来进行通信,所有变量都会定义在主内存中,如果线程对某一个变量进行修改,线程需要先将主存中的变量拷贝到工作内存中,操作完成后,再同步到主内存。因为工作内存中的变量会放入CPU的高速缓存中,而主内存的变量就在物理内存中,这样可以提高速度。
上面的代码执行流程为:
1,线程启动以后,各个线程都将主存变量flag=false读到自己的工作内存
2,子线程启动以后,停顿3秒,将变量修改为true,此时主线程进入while(true)循环,因为flag为false,所以一直循环
3,子线程修改以后,立即将该修改同步到主内存,此时主线程停顿1秒,读取到修改以后的值。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值