用户量都变大了,还不掌握一点解决并发编程三大问题的思路吗

掌握思路之前,需要先了解一个概念:
JAVA内存模型:这是一种规范,通过定义多种规则对编译器和处理器进行限制,主要用来解决可见性和有序性问题
java内存模型所涉及到的关键字:volatile字段final修饰符与对象的安全发布。ps:内存模型的底层实现:通过内存屏障来禁止重排序。

  1. 锁:锁是具备happens-before关系的,在解锁的时候,JVM会把缓存的内容刷新到内存上,保证修改的内容对其他线程的可见性
  2. volatitle:不能解决原子性问题,但是可以解决可见性问题,频繁的访问volatitle也会增加性能开销
  3. final:final与新建对象的发布问题是息息相关的,一个对象包含final修饰的实例字段时候,其他线程能够看到已经初始化的final实例字段,保证其可见性。

上述三点中,有个很重要的关系:happens-before这个关系里面包含七个规则,一个特性,如下
规则:

  1. 程序次序规则:在一个线程内,程序按照代码书写顺序来执行
  2. 管程锁定规则:管程是一种通用的同步原语,java中指的就是syncchronized。一个解锁操作先行发生于后面其他线程对同一个锁的加锁操作,这样才能保证可见性
  3. volititle变量规则:对于一个volititle变量的写操作先行发生于后面对这个变量的读操作
  4. 线程启动规则:Thread对象的start方法先行发生于此线程的每一个动作
  5. 线程终止规则:线程中所有操作先行发生于对此线程的终止检测。我们可以通过Thread.jion方法来确保线程已经执行结束
  6. 线程中断规则:线程interrupt()方法的调用要先行发生于被中断线程的代码检测终端事件的发生。因此可以通过interrupt方法来检测是否有中断发生
  7. 对象终结规则:一个对象初始化先行发生于它的finalize方法

特性:
传递性

至于原子性问题 ,这个主要是通过互斥锁来解决
原子性的问题的根本原因就是线程切换。在单核时代,同一时刻只有一个线程工作,禁用CPU中断就能禁止线程切换。多核时代,同一时刻可能有多个线程在执行,禁用CPU中断并不能解决原子性问题。
经过上述分析得出结论,同一时刻只有一个线程执行是解决原子性问题的必要条件,这个条件称之为互斥,保证共享变量的修改是互斥的,无论是单核还是多核,都可以保证其原子性。
下面是几个概念:
synchronized修饰普通变量和普通方法锁是当前对象即(this)synchronized修饰静态变量和方法锁是当前类的.class对象
受保护资源和锁之间的关联关系是N:1的关系,用一个锁去锁住资源,不能用多个锁去锁住资源
加锁的本质就是在锁对象的对象头写入当前线程的id

猜你喜欢

转载自blog.csdn.net/weixin_42683077/article/details/105755920