- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我有几个线程执行一些工作,然后必须进入休眠/等待不确定的时间。稍后他们都需要被叫醒并继续工作。我可以通过在对象上调用 wait()
,然后在需要恢复时在同一对象上调用 notifyall()
来实现此目的。在研究这个问题时,我发现了这个教程:http://tutorials.jenkov.com/java-concurrency/thread-signaling.html显然,通过将信号存储在信号类中并检查 while 循环内的信号成员变量来防止丢失信号和虚假唤醒是一种很好的做法。以下是教程中的代码示例:
public class MonitorObject{
}
public class MyWaitNotify3{
MonitorObject myMonitorObject = new MonitorObject();
boolean wasSignalled = false;
public void doWait(){
synchronized(myMonitorObject){
while(!wasSignalled){
try{
myMonitorObject.wait();
} catch(InterruptedException e){...}
}
//clear signal and continue running.
wasSignalled = false;
}
}
public void doNotify(){
synchronized(myMonitorObject){
wasSignalled = true;
myMonitorObject.notify();
}
}
}
这段代码可以工作,但我需要唤醒所有线程,而不仅仅是一个线程。如果我用 myMonitorObject.notifyAll();
替换 myMonitorObject.notify();
,这将不起作用,因为恢复工作的第一个线程将设置 wasSignalled
code> 标志为 false
,所有其他线程将被困在 while 循环中。
我做了一些更改,使我能够唤醒所有线程:
MonitorObject myMonitorObject = new MonitorObject();
boolean wasSignalled = false;
public void doWait(){
synchronized(myMonitorObject){
while(!wasSignalled){
try{
myMonitorObject.wait();
} catch(InterruptedException e){
}
}
}
}
public void resetSignal() {
wasSignalled = false;
}
public void doNotifyAll() {
synchronized(myMonitorObject){
wasSignalled = true;
myMonitorObject.notifyAll();
}
}
但这不是一个很好的解决方案,因为现在我无法只唤醒一个线程,并且我必须在 doNotify
之后重置信号,然后才能再次使用 doWait。
有没有人有一个解决方案,使我能够在正在等待的线程上使用 notify
或 notifyAll
?
关于该示例的一件事我不明白,为什么我必须使用单独的 MonitorObject 类?为什么我不能只在 MyWaitNotify
类本身上调用 wait
和 notify
?
像这样:
public class WaitNotify {
boolean wasSignalled = false;
public void doWait(){
synchronized(this){
while(!wasSignalled){
try{
wait();
} catch(InterruptedException e){
}
}
}
}
public void resetSignal() {
wasSignalled = false;
}
public void doNotifyAll() {
synchronized(this){
wasSignalled = true;
notifyAll();
}
}
}
这似乎有效,有什么理由我不应该这样做?
最佳答案
使用生成整数。当一个线程阻塞时,阻塞直到生成整数改变。在调用 notifyAll
之前,增加生成整数。
关于Java,等待并notifyAll : guard against spurious wakeups,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35108642/
我有几个线程执行一些工作,然后必须进入休眠/等待不确定的时间。稍后他们都需要被叫醒并继续工作。我可以通过在对象上调用 wait() ,然后在需要恢复时在同一对象上调用 notifyall() 来实现此
如果我会写: int selectedChannels = selector.select();Set selectedKeys = selector.selectedKeys();if ( sele
我试图了解条件变量情况下虚假唤醒与丢失唤醒之间的区别。以下是我试过的一小段代码。我知道在这种情况下“消费者”可能会在没有任何通知的情况下醒来,因此等待需要检查谓词。 但是 wait with pred
这里的一些评论让我感到困惑!我以为我知道这一点,上帝知道我已经编写了大量的 MT 代码,但已经有一段时间了...... FWIK 通知/通知所有 通知:从waitset中选出一个线程移到entryse
我正在编写另一个 NIO 服务器。有一个选择器线程执行读取、处理(大多数情况下)和写入(下面的伪代码,不是真正的 Java): while (true) { select(); for
在下面的语句中,即使没有调用通知,wait() 方法也会执行,但是 below() 语句仅在 laurel 之后执行 线程完成它的执行。 我尝试使用其他对象来锁定 hardy block 的同步,这次
我在 iOS 上的 gdx 游戏中随机出现了一些崩溃。它在其他平台上运行没有任何问题。 当应用程序退出时,我在我的 robovm 终端中得到了这个: 9/17/15 1:05:29 PM: [ERRO
我有一台服务器,它会为每个安全连接的客户端创建一个新线程。如果我使用线程池,这意味着我将同时拥有有限数量的客户端。然而,这意味着我不能监听所有客户端的端口。 我的想法是让客户端发送一个 UDP 数据包
如何以编程方式将电源选项中“唤醒时需要密码”的值更改为 false使用 C#。目前它需要密码才能在计算机从 sleep 中唤醒时解锁 手动:电源选项->高级设置->平衡-> 唤醒时需要密码-> 电池:
两种方法Thread#run and Thread#wakeup不知何故不同,但我不清楚。有人可以提供一对差异最小的代码(即差异仅在一个代码中使用 run,在另一个代码中使用 wakeup),显示不同
在 Ruby 中,Thread#run 和 Thread#wakup 有什么区别? RDoc 指定 scheduler 不使用 Thread#wakeup 调用,但这是什么意思?何时使用唤醒 与 运行
有人知道 iOS 8 上的这种异常是什么吗? === 来自崩溃报告 === Exception Type: EXC_RESOURCE Exception Subtype: WAKEUPS Except
我是一名优秀的程序员,十分优秀!