当前位置: 首页 > 后端技术 > Java

Synchronized&Lock&ReentrantLock区别

时间:2023-04-01 20:05:27 Java

Synchronized&LockSynchronized可用于锁定类、方法和代码块;Lock只能作用于代码块。synchronized不需要手动获取和释放锁,更简单;如果Lock没有unlock(),可能会导致一些问题。Lock可以通过lock()判断是否已经获取到锁,而Synchronized则不能。Synchronized和ReentrantLock都是可重入锁。Layer)ReentrantLock功能更全面,支持公平和非公平模式,支持中断和放弃锁获取,支持Condition实现线程间调度,使用更灵活,除非需要使用ReentrantLock的高级功能。尽量使用Synchronized,比较简单。JVM原生支持Synchronized锁的升级顺序:无锁>偏向锁>轻量级锁>重度锁Synchronized使用的锁存储在Java对象头的MarkWord中,存储同步状态、logo、hashcode等信息GC状态。大多数情况下,锁的使用不存在多线程竞争,总是由同一个线程获取;因此,引入了偏向锁,以降低线程首次获取锁的成本;偏向锁会偏向第一个访问锁的线程,程序运行时,只有一个线程访问同步锁,不存在多线程争用,则该线程不需要触发同步,直接加一个偏向锁给线程轻量级锁,当发生锁竞争时,偏向锁会升级为轻量级锁,轻量级锁为自旋锁;轻量级锁的设计思想是,如果持有锁的线程可以在短时间内释放锁,则等待线程不需要进行上下文切换,而只进行几次自旋等待,持有线程锁可以在释放锁后立即获取锁,从而避免了上下文切换的开销(上下文切换比执行CPU指令开销大得多)。权重锁线程自旋需要占用CPU,所以需要设置一个自旋等待的最大时间。当持有锁的线程执行时间超过自旋等待的最大时间,锁还没有释放时,竞争锁的线程就会停止自旋,进入阻塞状态。此时会升级为权重级别的锁,JDK1.6引入自适应自旋锁,自旋时间不再固定,而是由同一把锁上的最后一次自旋时间和锁拥有者的状态决定,这基本上可以认为是线程上下文切换的一个时序参考:https://blog。csdn.net/m0_6965...