Java 并发编程笔记 第五章:共享模型_内存

网课链接: 黑马程序员java并发.

第五章 共享模型之内存

章节总结

本章重点讲解了JMM(Java Memory Model)中的

  • 可见性: 由JVM缓存优化引起
  • 有序性: 由JVM指令重排序优化引起
  • happens-before 规则

原理方面

  • CPU指令并行
  • volatile

模式方面

  • 两阶段终止模式的volatile改进
  • 同步模式之balking

5.1 Java内存模型

JMM 即 Java Memory Model,它定义了主存(共享内存)、工作内存(线程私有)抽象概念,底层对应着 CPU 寄存器、缓存、硬件内存、 CPU 指令优化等。
JMM 体现在以下几个方面

  • 原子性 - 保证指令不会受到线程上下文切换的影响
  • 可见性 - 保证指令不会受 cpu 缓存的影响
  • 有序性 - 保证指令不会受 cpu 指令并行优化的影响

5.2 可见性

1. 退不出循环

退不出循环的问题可以归咎于JIT编译器的特性, 在JIT编译器中. 当一段代码出现循环, 编译器会将读取的值存入线程的缓存. 因为线程缓存只能在线程内进行更改, 所以线程会进入死循环.

在这里插入图片描述

解决方法

  • 使用volatile
  • 它可以用来修饰成员变量和静态成员变量(放在主存中的变量),他可以避免线程从自己的工作缓存中查找变量的值,必须到主存中获取它的值,线程操作 volatile 变量都是直接操作主存
public static volatile boolean run = true;

2. 可见性 与 原子性

保证的是在多个线程之间,一个线程对 volatile 变量的修改对另一个线程可见, 不能保证原子性,仅用在一个写线程,多个读线程的情况。

注意

synchronized 语句块既可以保证代码块的原子性,也同时保证代码块内变量的可见性。但缺点是 synchronized 是属于重量级操作,性能相对更低。

如果在前面示例的死循环中加入 System.out.println() 会发现即使不加 volatile 修饰符,线程 t 也能正确看到 对 run 变量的修改了,想一想为什么?

  • 因为 printIn() 方法使用了 synchronized 同步代码块,可以保证原子性与可见性,它是 PrintStream 类的方法。

3. 终止模式 之 两阶段终止模式

Two Phase Termination
在一个线程T1中如何“优雅”终止线程T2? 这里的优雅就是指给线程一个料理后事的机会
使用 volatile 关键字来实现两阶段终止模式。

错误思路

与两阶段终止模式相反的就是

  • 使用线程对象的stop()方法停止线程
    • stop方法会杀死线程, 如果线程锁住了共享资源, 那么当它杀死后其他线程将永远无法获取锁
  • 使用 System.exit() 方法停止线程
    • 用力过猛了, 终止线程编程终止程序
public class Code_02_Test {
   
	public static void main(String[] args) throws InterruptedException {
   
		Monitor monitor = new Monitor();
		monitor.start();
		Thread.sleep(3500);
		monitor.stop();
	}
}

class Monitor {
   

	Thread monitor;
	// 设置标记,用于判断是否被终止了
	private volatile boolean stop = false;
	/**
	 * 启动监控器线程
	 */
	public void start() {
   
		// 设置线控器线程,用于监控线程状态
		monitor = new Thread() {
   
			@Override
			public void run() {
   
				// 开始不停的监控
				while (true) {
   
					if(stop) {
   
						System.out.println("处理后续任务");
						break;
					}
					
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值