StampedLock通过戳记机制支持写锁、悲观读锁和乐观读锁,提升读多写少场景性能。其核心是乐观读无需加锁,先读取后验证戳记是否失效,若被修改则升级为悲观读锁重试。示例中distanceFromOrigin方法用tryOptimisticRead获取戳记,读取后调用validate校验,确保数据一致性。注意戳记不可重用,必须用unlockWrite或unlockRead释放对应锁,且不支持重入与synchronized混用。正确使用可显著提高并发吞吐量。

StampedLock 是 Java 8 引入的一种高性能读写锁机制,相比传统的 ReentrantReadWriteLock,它在读多写少的场景下表现更优。其核心特点是使用了“戳记(stamp)”机制来控制锁的获取与释放,支持三种模式:写锁、悲观读锁和乐观读锁。
基本概念与特点
StampedLock 的主要优势在于支持乐观读锁。在大量读操作并发时,乐观读可以避免阻塞,提升吞吐量。与传统读锁不同,乐观读不会阻塞写线程,但需要在读取完成后验证数据是否被修改过。
关键点:
- 锁的获取返回一个 long 类型的戳记(stamp)
- 释放锁或验证状态时需传入该戳记
- 不支持重入,同一个线程重复加锁可能导致死锁
- 不能与 synchronized 混用管理临界区
三种锁模式的使用方式
1. 写锁(Write Lock)
立即学习“Java免费学习笔记(深入)”;
写锁是独占锁,获取时会阻塞所有其他读写操作。调用 writeLock() 方法获取戳记,完成操作后必须调用 unlockWrite(stamp) 释放。
StampedLock lock = new StampedLock();long stamp = lock.writeLock();
try {
// 修改共享数据
} finally {
lock.unlockWrite(stamp);
}
2. 悲观读锁(Read Lock)
标准的读锁,允许多个线程同时读。调用 readLock() 获取戳记,处理完后调用 unlockRead(stamp) 释放。
用 php + mysql 驱动的在线商城系统,我们的目标为中国的中小企业及个人提供最简洁,最安全,最高效的在线商城解决方案,使用了自建的会员积分折扣功能,不同的会员组有不同的折扣,让您的商店吸引更多的后续客户。 系统自动加分处理功能,自动处理会员等级,免去人工处理的工作量,让您的商店运作起来更方便省事 采用了自建的直接模板技术,免去了模板解析时间,提高了代码利用效率 独立开发的购物车系统,使用最
try {
// 读取共享数据
} finally {
lock.unlockRead(stamp);
}
3. 乐观读锁(Optimistic Read)
最轻量级的读模式,不加锁直接读取,之后通过 validate(stamp) 判断读期间是否有写操作发生。
long stamp = lock.tryOptimisticRead();// 读取数据
if (!lock.validate(stamp)) {
// 被修改,升级为悲观读锁
stamp = lock.readLock();
try {
// 重新读取数据
} finally {
lock.unlockRead(stamp);
}
}
实际应用示例
考虑一个包含坐标点的类,频繁读取而较少更新:
class Point {private double x, y;
private final StampedLock lock = new StampedLock();
void move(double deltaX, double deltaY) {
long stamp = lock.writeLock();
try {
x += deltaX;
y += deltaY;
} finally {
lock.unlockWrite(stamp);
}
}
double distanceFromOrigin() {
long stamp = lock.tryOptimisticRead();
double currentX = x, currentY = y;
if (!lock.validate(stamp)) {
stamp = lock.readLock();
try {
currentX = x;
currentY = y;
} finally {
lock.unlockRead(stamp);
}
}
return Math.sqrt(currentX * currentX + currentY * currentY);
}
}
这个例子中,distanceFromOrigin 使用乐观读提高了读性能,在无写操作时几乎无开销,一旦检测到冲突则退化为安全读锁。
注意事项与最佳实践
使用 StampedLock 需注意以下几点:
- 戳记不可重用,每次加锁生成新值
- 不要在持有锁时执行耗时或可能阻塞的操作
- 乐观读期间不应修改任何状态
- validate 返回 false 并不总是意味着数据被改,可能是其他写锁短暂获取
- 建议配合 try-finally 确保锁正确释放
基本上就这些。StampedLock 在高并发读场景下非常有用,特别是能有效减少读写之间的相互影响。掌握好乐观读的使用模式,能显著提升程序性能。









