1.ReentrantLock的实现原理
ReentrantLock是一个可重入的互斥锁,具有尝试非阻塞地获取锁、可中断的锁获取、支持公平性等特点。ReentrantLock通过内部类Sync实现核心功能,Sync继承了AQS类(构建锁和其他同步组件的框架)。AQS通过int型的成员变量表示同步状态,通过内置的FIFO来管理线程的排队等待。
可重入性:
当一个线程获取了 ReentrantLock
后,它可以再次获取该锁而不会造成死锁,这是因为 ReentrantLock
会记录当前拥有锁的线程以及该线程获取锁的次数。只有当该线程释放锁的次数与它获取锁的次数相同时,锁才会被真正释放。
锁获取:
- lock():调用此方法会使当前线程尝试获取锁。如果锁不可用,当前线程会被阻塞,直到锁可用。
- tryLock():尝试非阻塞地获取锁。如果锁可用,当前线程获取锁并立即返回 true;否则返回 false,不会等待。
- tryLock(long timeout, TimeUnit unit):尝试在指定的时间内获取锁。如果在给定时间内锁可用,当前线程获取锁并返回 true;如果超时或锁不可用,返回 false。
2.垃圾回收算法
垃圾回收器用于自动管理Java内存。垃圾回收器算法有Serial GC、Parallel GC/Parallel Old GC、CMS以及G1等算法
Serial GC:Serial GC是单线程的垃圾回收器,垃圾回收时会暂停所有用户线程(STW)、包括新生代的Minor GC和老年代的Major GC,采用标记清除或标记压缩算法。
Parallel GC:Parallel GC是Serial GC的并行版本,在多核环境下使用多个线程进行垃圾回收,回收过程中暂停所有用户线程。多核环境行性能较好,显著缩短STW时间;并发场景下,并行处理可能导致系统负载较大;采用复制算法进行垃圾回收。
CMS:初始标记、并发标记、重新标记、并发清除。大部分工作并发执行,减少STW,适用于响应高场景。采用标记-清除算法,碎片化严重,需定期进行并发压缩。
G1:区域化管理(分代,即新生代和老年代)、并发标记、空间回收、完整GC。采用标记-整理算法进行实时垃圾回收,大量小对象回收不如其他收集器。
3.Redis的分布式锁实现
Redis的分布式锁实现依赖于其原子性和高性能。
3.1.使用SETNX命令
SERNX(SET if Not eXists)命令用于在键不存在时设置键值。该命令可用于简单实现分布式锁:
- 加锁:SETNX lockKey;
- 如果lockKey不存在,SETNX会设置键并返回1表示成功获取锁
- 如果lockKey存在,SETNX不会设置键并返回9表示获取锁失败
- 解锁:使用DEL lockKeyy命令删除锁
3.2 使用SET命令带过期时间
SET命令可以结合EX或PX选项设置键的过期时间,避免锁无限期持有
-
加锁:
SET lockKey value EX 30
或SET lockKey value PX 30000
EX
后跟秒数,PX
后跟毫秒数,表示锁的过期时间。NX
选项确保只在键不存在时设置值。
-
解锁:同样使用
DEL lockKey
命令。
3.3 使用Lua脚本与Redis的call方法结合
3.4 RedLock算法
RedLock是一种更安全的分布式锁实现,它通过在多个Redis实例上尝试获取锁提高锁的可靠性。
- 客户端获取当前时间戳。
- 依次尝试在多个Redis实例上加锁,每个实例都需要设定相同的过期时间和随机字符串(nonce)。
- 客户端计算加锁操作的总时间,并将其与指定的超时时间进行比较。如果总时间小于超时时间,并且超过一半的Redis实例加锁成功,则认为加锁成功。否则,客户端需要在所有实例上尝试解锁操作。
3.5 注意事项:
- 安全性:确保解锁操作只能由加锁的客户端执行,避免误删其他客户端的锁。
- 死锁预防:设置锁的过期时间以避免死锁。
- 重试机制:在获取锁失败时,可能需要重试。
- 锁的公平性:确保所有客户端都有公平的机会获取锁。
4.强引用、软引用、弱引用、虚引用
在Java中,对象引用分为强、软、弱、虚等四种引用。四种对象引用的强度依次减弱,对GC也有不同的影响。
强引用:
强引用是Java中最常见的引用类型。当对象被强引用关联时,它将一直被保留在内存中,直到强引用被显式地断开(例如,将其设置为null
)。只要强引用存在,垃圾收集器就不会回收这个对象。
Object obj = new Object()
软引用:软引用关联的对象在内存不足时才会被垃圾收集器回收。软引用通常用于实现内存敏感的缓存,可以通过java.lang.ref.SoftReference
类创建
SoftReference<Object>softRef = new SoftReference<>(new Object)
弱引用:只要垃圾收集器运行,弱引用关联的对象就可能被回收,不管当前内存是否充足。弱引用通常用于实现缓存等需要快速响应内存变化的场景。(ThreadLocal)
WeakReference<Object>weakRef = new WeakRefernce<>(new Object);
虚引用:虚引用几乎不阻止垃圾收集器回收关联的对象。虚引用主要用于跟踪对象被回收的状态,当对象即将被回收时,可以将虚引用加入到一个引用队列中,从而可以执行一些清理工作。
标签:面试题,加锁,回收,获取,线程,引用,GC,他人 From: https://www.cnblogs.com/kzf-99/p/18083164