8 java concurrency multithreading semaphore synchronisation
我有以下类型的代码:
synchronized block1 {
//only one thread in the block
}
{lot of code where synchronization not necessary}
synchronized block2 {
//only one thread in the block.
//All the threads that executed block1 before this thread should have already executed this block.
}
Run Code Online (Sandbox Code Playgroud)
每个线程首先以相同的顺序执行block1,non synchronized block和block2.
如果线程T1在线程T2之前执行block1,那么T1应该在T2之前执行block2.有两个以上的线程.
有没有办法在java中实现这一点?
据我了解,关键部分 #2 必须按照与关键部分 #1 相同的顺序执行
如果线程 T1 在线程 T2 之前执行 block1,则 T1 应该在 T2 之前执行 block2。有两个以上的线程。
然后可以使用队列来确保执行顺序。
private Object lock = new Object();
private Queue<Thread> threadQueue = new ArrayDeque<>();
// /sf/ask/2264729841/
public void executeCriticalSectionsInOrder() throws InterruptedException {
// Critical Section #1
synchronized (lock){
// synchronized code #1
// Add self to queue
threadQueue.add(Thread.currentThread());
}
// {lot of code where synchronization not necessary}
// Critical Section #2
synchronized (lock) {
//All the threads that executed block1 before this thread should have already executed this block.
// Wait turn
Thread t = threadQueue.element(); // Do not remove until it is self
while (t != Thread.currentThread()) {
lock.wait();
// After sleep try again
t = threadQueue.element();
}
// Verified own turn. Update status
threadQueue.remove();
// synchronized code #2
lock.notifyAll(); // Awake any waiting thread after exiting section.
}
Run Code Online (Sandbox Code Playgroud)
但是,如果一个线程死亡/退出而没有将其自身从队列中删除,则后续线程将被无限期地阻塞。也许添加一个finally块来进行内务处理?
注意:在Nicholas Robinson 的回答中,建议使用位置顺序而不是队列,这似乎更有效。