1. 乐观锁和悲观锁
2. 轻量级锁和重量级锁
3. 自旋锁和挂起等待锁
4. 普通互斥锁和读写锁
5. 可重入锁和不可重入锁
6. 公平锁和非公平锁(这里的公平表示遵循先来后到的规则)
? 详细的可以看还有synchronized的优化过程:对于synchronized的总结-CSDN博客
? 对于synchronized的来说它是自适应的,不是读写锁,是可重入锁,是非公平锁。?
? 全称Compare and swap,字面意思:”比较并交换比较并且交换,的是内存和cpu寄存器。借助这个操作,就可以原子的完成很多复杂的操作,达成“无锁化编程”的效果。(CAS也不是万能的)?
1.简单的工作原理:?
boolean CAS(address, expectValue, swapValue) {
if (&address == expectedValue) {
? &address = swapValue;
? ? ? ?return true;
? }
? ?return false;
}
? 我们可以带入一个场景有俩个线程同时要对address进行++,他会先判断address和expectValue是否相等,如果相等就会交换,不相等就不会进行交换。
3.Java标准库提供的原子类
?
4.CAS的ABA问题
? 你可以理解为你买的是一个翻新机,你因为你买的是一个新机器,实际上买到的是一个二手机器。外表看起来崭新的,但是已经是别人用剩的。CAS在使用的时候,关键要点是判定当前内存的值是否和寄存器的值是一样的,就进行修改,不一样就啥也不做。
?那对于ABA问题来说,什么时候会有bug呢???
? 还可以假设一种情况你去银行取钱,结果卡住了,你多点了一下,此时产生了俩个线程,去尝试进行扣款操作(CAS)了,你会发现多按的一下并没有成功,因为俩个值并不相同就不会再扣一次,但是如果有第三个线程突然存了钱,那就出大问题了,就可能会多点的那一下扣去了。
对于ABA的解决方案:
? 1. 约定数据变化是单向的(只能增加或者减少),不能是双向的。
? 2.对于本身就必须双向变化的数据可以引入版本号,版本号这个数字就只能增加,不能减少了。
? synchronized 背后设计到了很多的“优化手段”。
? 1. 锁升级:偏向锁->轻量级锁->重量级锁
? 2. 锁消除:自动干掉不必要的锁。
? 3. 锁粗化: 把多个细粒度的锁合并成一个粗细粒度的锁,减少了锁竞争的开销。
?可以看这一篇:对于synchronized的总结-CSDN博客