synchronized的内存语义-内存可见性

synchronized的内存可见性很垃圾,慎用,也给了大家一个提醒,synchronized主要是用来互斥,内存可见性尽量用volatile保持

例子

public class TestSyncMemorySee {
    static boolean r=false;
    static Object o=new Object();

    public static void main(String[] args) {
        Thread t1=new Thread(()->{
           synchronized (o){
               while (!r){}
           }
            System.out.println(Thread.currentThread().getName()+"end");
        },"t1");

        Thread t2=new Thread(()->{
            r=true;
            System.out.println(Thread.currentThread().getName()+"end");
        },"t2");

        t1.start();
        try {
            Thread.sleep(1000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        t2.start();

    }
}

上面代码t1线程先开始执行,按照synchoinzed的内存可见性,获取锁后会刷新工作内存,从主内存拉取共享变量r=false,后面这个值是不会改变的,就算t2线程在1秒后改变了r=true,但是t1线程还在傻循环,由此可以推测synchronized的内存可见性只限于一次读取,解决办法是r变量加volatile修饰,volatile的内存可见性是无论什么时候读都是通过刷新工作内存,从主内存读取,底层是通过总线锁实现,汇编指令是lock。synchorinzed保持内存可见性底层还不太清楚,推测是简单的一次刷新工作内存,没有在cpu加锁

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值