Discuss / Java / 代码例子中的疑问

代码例子中的疑问

Topic source

不惑之年

#1 Created at ... [Delete] [Delete and Lock User]
 public double distanceFromOrigin() {
        long stamp = stampedLock.tryOptimisticRead(); // 获得一个乐观读锁
        // 注意下面两行代码不是原子操作
        // 假设x,y = (100,200)
        double currentX = x;
        // 此处已读取到x=100,但x,y可能被写线程修改为(300,400)
        double currentY = y;
        // 此处已读取到y,如果没有写入,读取是正确的(100,200)
        // 如果有写入,读取是错误的(100,400)
        if (!stampedLock.validate(stamp)) { // 检查乐观读锁后是否有其他写锁发生
            stamp = stampedLock.readLock(); // 获取一个悲观读锁
            try {
                currentX = x;
                currentY = y;
            } finally {
                stampedLock.unlockRead(stamp); // 释放悲观读锁
            }
        }
        return Math.sqrt(currentX * currentX + currentY * currentY);
    }

关于这块代码,想问问老师,这里释放悲观读锁之后

 stampedLock.unlockRead(stamp); // 释放悲观读锁

返回以下结果之前

return Math.sqrt(currentX * currentX + currentY * currentY);

有一个写线程获取到了锁,并把(x,y)从(1,2)变成了(3,4),但是此线程读到的结果是 Math.sqrt(1*1 + 2*2),这算不算返回了错误数据呢?

#2 Created at ... [Delete] [Delete and Lock User]

卡极限操作是吧

你这个疑问之前已经有人问过了,往下看@萧雨千叶的提问:if和return之间发生了写入岂不是读到旧数据了?廖老师对此也回复解释得非常清楚,建议看看。

🌙

#4 Created at ... [Delete] [Delete and Lock User]

我的理解是不会,读数据要重新获取锁

21

#5 Created at ... [Delete] [Delete and Lock User]

锁的作用是保证,这个是一个原子操作

currentX = x;
currentY = y;

你说的那个顶多算过时的数据,不是错误数据。


  • 1

Reply