首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >ReentrantReadWriteLock是否在writeLock锁定时读取?

ReentrantReadWriteLock是否在writeLock锁定时读取?
EN

Stack Overflow用户
提问于 2014-04-15 20:13:36
回答 1查看 267关注 0票数 1

我研究ReentrantReadWriteLock

我编写了简单的测试代码(我知道使用Thread.sleep()不能保证可预测的结果,但我认为我很幸运:):

代码语言:javascript
复制
public class RWLock {
    private static String val = "old";
    private static ReadWriteLock lock = new ReentrantReadWriteLock();
    private static long time =  System.currentTimeMillis();
    public void read() {
        try {
            lock.readLock().lock();
            System.out.println("read " + val +" - "+(System.currentTimeMillis()-time));
            Thread.sleep(300);
        } catch (InterruptedException e) {

        } finally {
            lock.readLock().unlock();
        }
    }

    public void write() {
        try {
            lock.writeLock().lock();
            val = "new";
            System.out.println("write " + val+" - "+(System.currentTimeMillis()-time));
            Thread.sleep(10000);
        } catch (InterruptedException e) {

        } finally {
            lock.writeLock().unlock();
        }
    }
}

class Tester {
    public static void main(String[] args) throws InterruptedException {

        new MyThreadRead().start();

        Thread.sleep(400);
        new MyThreadWrite().start();
    }

}

class MyThreadRead extends Thread {
    @Override
    public void run() {
        for (int i = 0; i < 10; i++) {
            new RWLock().read();
            try {
                Thread.sleep(200);
            } catch (InterruptedException e) {
            }
        }
    }
}

class MyThreadWrite extends Thread {
    @Override
    public void run() {
        new RWLock().write();
    }
}

产出:

代码语言:javascript
复制
read old - 0
write new - 401
read new - 10401
read new - 10902
read new - 11402
read new - 11902
read new - 12402
read new - 12902
read new - 13402
read new - 13902
read new - 14402

10401 - 401 == 10000

10000是写作的时候了。

正如我所理解的,二读线程不能在写之前完成。因此,写作和二读并行执行。这对我来说是不可预测的行为。

你觉得那个怎么样?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2014-04-15 20:40:42

也许你有更多的睡眠()电话比你意识到的多。MyThreadRead#run()和RWLock()#read()中的睡眠调用加起来可达500 ms。下面是发生的事情。

代码语言:javascript
复制
At T=0, the reader thread grabs the read lock and sleeps for 300ms.
At T=300, the reader releases the lock, and then sleeps for another 200ms.
At T=400, the writer grabs the write lock and sleeps for ten seconds,
At T=500, the reader tries to grab the read lock, but it is blocked by the writer.
At T=10400, the writer gives up the lock, and then the reader gets to go round
   its loop nine more times.

P.S.:将lock()调用移出try/finally语句。例如,

代码语言:javascript
复制
...lock()
try {
    ...
} finally {
    ...unlock();
}

这样,如果lock()调用抛出一个异常,那么将不会调用unlock()。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/23093581

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档