java线程安全与内存模型

内存模型:主内存 > 工作内存(线程私有内存) > cpu高速缓存

主内存与工作内存间 同步操作有:

1、lock (锁定主内存数据) ;unlock(解锁主内存数据)

2、read(读取主内存数据);load(将读取的主内存数据 载入到 工作内存中)

3、use(使用工作内存数据);assign(赋值工作内存数据)

4、store(储存工作内存数据);write(工作内存数据回写到主内存)

数据的使用按【1】【2】【3】【4】顺序执行,除了【3】外,其余操作不允许单独出现

备注:lock操作会将工作内存相同数据清空,unlock操作前会将工作内存数据store、write到主内存

原子性、可见性、有序性

上述操作均为原子性操作;

可见性:A线程修改数据,B线程立刻得知新值;

有序性:A线程内部操作均为有序,A观察B线程内部操作均为无序。

  针对有序性有先行发生原则

  程序次序规则:一个线程内,操作有序(顺序)

  管程锁定规则:前一unlock操作先行后一lock操作【时间上】

  volatile规则:volatile变量前一写操作先行后一读操作【时间上】

  线程启动规则:Thread对象的start()方法先于此线程的每一操作

  线程终止规则:线程的所有操作都先于此线程的终止

  线程中断规则:对线程的interrupt()方法的调用先于被中断线程的代码检测到中断事件发生

  对象终结规则:一个对象的初始化先于finalize()方法的开始

  传递性:A先于B,B先于C,则A先于C

 

精华++

彩蛋

public class Test1 {
    static volatile boolean fg = false;
    static int i = 0;

    public static void main(String[] args) throws InterruptedException {
        /**
         * 测试volatile 写操作先于读操作【时间上】
         * 运用变量fg、i
         */
        new Thread(() -> {
            int i = 0;
            while (i < 50) {
                if (Test1.fg) {//与下面Thread相反
                    Test1.i++;
                    Test1.fg = !Test1.fg;
                    i++;
                }
            }
        }).start();
        new Thread(() -> {
            int i = 0;
            while (i < 50) {
                if (!Test1.fg) {//与上面Thread相反
                    Test1.i++;
                    Test1.fg = !Test1.fg;
                    i++;
                }
            }
        }).start();
        Thread.sleep(1000);//保证两个子线程运行完毕
        System.out.println(i);//始终是100,为线程安全
        System.exit(0);
    }
}

 

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值