zoukankan      html  css  js  c++  java
  • Java高并发-Java内存模型和线程安全

    一、原子性

    原子性是指一个操作是不可中断的。即使在多个线程一起执行的时候,一个操作一旦开始,就不会被其它线程干扰。

    i++是原子操作吗?
    不是,包含3个操作:读i,i=i+1,写i
    
    32位的机子上读取64位的long型也不是原子操作
    

    二、有序性

    2.1 举例

    在并发时,程序的执行可能会出现乱序

    2.2 步骤

    一条指令的执行是可以分为很多步骤的:

    • 取指IF
    • 译码和取寄存器操作数ID
    • 执行或者有效地址计算EX
    • 存储器访问MEM
    • 写回WB

    流水线执行指令

    分析:

    指令分解成不同阶段
    假设一条指令消耗一个CPU时钟周期
    5个人生产一个产品,5个人同时工作
    
    a=b+c
    读b
    读c
    计算b+c,结果放到a
    写a
    
    

    分析:

    进行优化,使气泡尽可能的少
    

    分析:

    调整指令顺序,可以消除气泡
    

    三、可见性

    3.1 定义

    可见性是批当一个线程修改了某一个共享变量的值,其他线程是否能够立即知道这个修改。

    • 编译器优化
    • 硬件优化(如写吸收,批操作)
    批量操作,把操作进行积累,只把最终结果写入
    

    3.2 Java虚拟机层面的可见性

    http://hushi55.github.io/2015/01/05/volatile-assembly

    public class VisibilityTest extends Thread {
    	private boolean stop;
    
    	public void run() {
    		int i = 0;
    		while (!stop) {
    			i++;
    		}
    		System.out.println("finish loop,i=" + i);
    	}
    
    	public void stopIt() {
    		stop = true;
    	}
    
    	public boolean getStop() {
    		return stop;
    	}
    
    	public static void main(String[] args) throws Exception {
    		VisibilityTest v = new VisibilityTest();
    		v.start();
    
    		Thread.sleep(1000);
    		v.stopIt();
    		Thread.sleep(2000);
    		System.out.println("finish main");
    		System.out.println(v.getStop());
    	}
    }
    

    分析:

    stop变量加volatile就不会有这个问题了
    

    四、Happen-Before

    五、线程安全的概念

    指某个函数、函数库在多线程环境中被调用时,能够正确地处理各个线程的局部变量 ,使程序功能正确完成。

    i++在多线程下访问的情况:

  • 相关阅读:
    整合Sleuth
    idea springboot 微服务批量启动
    思维的八层境界(深度好文)
    【格局视野】三色需求与工作层次
    【阅读推荐】改变你思维模式的书单
    【软件架构】七款代码味道识别工具
    【软件架构】代码重构之道
    【Android】EventBus 源码解析
    【软件架构】IM架构设计(安卓版)
    【设计模式】Java版设计模式的类图汇总
  • 原文地址:https://www.cnblogs.com/okokabcd/p/8724901.html
Copyright © 2011-2022 走看看