【Java深入学习03(happens-before规则)】学向勤中得,萤窗万卷书。这篇文章主要讲述Java深入学习03:happens-before规则相关的知识,希望能为你提供帮助。
java深入学习03:happens-before规则
为什么会有happens-before 规则?
因为jvm会对代码进行编译优化,指令会出现重排序的情况,为了避免编译优化对并发编程安全性的影响,需要happens-before规则定义一些禁止编译优化的场景,保证并发编程的正确性。
1. 规则一:程序的顺序性规则一个线程中,按照程序的顺序,前面的操作happens-before后续的任何操作。
对于这一点,可能会有疑问。顺序性是指,我们可以按照顺序推演程序的执行结果,但是编译器未必一定会按照这个顺序编译,但是编译器保证结果一定==顺序推演的结果。
2. 规则二:volatile规则
对一个volatile变量的写操作,happens-before后续对这个变量的读操作。
3. 规则三:传递性规则
如果A happens-before B,B happens-before C,那么A happens-before C。
4.规则四:管程中的锁规则
对一个锁的解锁操作,happens-before后续对这个锁的加锁操作。
5.规则五:线程start()规则
主线程A启动线程B,线程B中可以看到主线程启动B之前的操作。也就是start() happens before 线程B中的操作。
6.规则六:线程join()规则
主线程A等待子线程B完成,当子线程B执行完毕后,主线程A可以看到线程B的所有操作。也就是说,子线程B中的任意操作,happens-before join()的返回。
这些规则背后的道理
在程序运行过程中,所有的变更会先在寄存器或本地cache中完成,然后才会被拷贝到主存以跨越内存栅栏(本地或工作内存到主存之间的拷贝动作),此种跨越序列或顺序称为happens-before。
注:happens-before本质是顺序,重点是跨越内存栅栏
通常情况下,写操作必须要happens-before读操作,即写线程需要在所有读线程跨越内存栅栏之前完成自己的跨越动作,其所做的变更才能对其他线程可见。
推荐阅读
- 使用Fiddler对APP进行弱网测试
- 报错RuntimeError: Model class apps.user.models.User doesn't declare an explicit app_label and isn&
- Android开机自启动应用
- Android001 开发环境安装(详细)
- 浅谈物联网操作系统选择,浏览器比安卓更合适!
- Android中三种创建监听器的方法
- android常用控件和布局
- [Trouble shooting] Alt-A shortcut taken by another app and conflict with Emacs' M-a
- Android Activity间跳转与传递数据