【发布时间】:2017-06-15 19:58:35
【问题描述】:
在我看来,Object.wait 的超时版本似乎很少按原样使用。这是因为:
- 该方法不处理虚假唤醒。
- 该方法没有表明它是否由于通知或超时而返回。
带有谓词作为参数的C++ version 似乎使它正确。带有签名的Object中对应的Java方法
boolean wait(long timeOutMillis, BooleanSupplier condition)
可以方便地使用如下:
Object obj = ...;
BooleanSupplier condition = ...;
synchronized (obj) {
if (obj.wait(1000, condition)) {
// condition is fulfilled
} else {
// timeout happened
}
}
作为一种解决方法,我可以使用以下丑陋的辅助方法:
public static boolean safeWait(Object waitObject, long timeOutMillis, BooleanSupplier condition) throws InterruptedException {
if (condition.getAsBoolean()) {
return true;
}
long rest = timeOutMillis;
while (true) {
long t0 = System.currentTimeMillis();
waitObject.wait(rest);
long t1 = System.currentTimeMillis();
long waited = t1 - t0;
if (condition.getAsBoolean()) {
return true;
}
rest = rest - waited;
if (rest <= 0) {
return false;
}
}
}
我最好提出一些问题:
- 我说得对吗,它坏了?
- 他们为什么不解决这个问题?
- 有没有更好的方法来解决这个问题?
【问题讨论】:
-
很难用,但不坏。这就是为什么您应该很少直接使用这些方法。使用来自
java.util.concurrent的更高级别的构造。 -
回答您的问题:不需要,可以。
-
取决于“损坏”是否意味着它没有做你希望它做的事情,或者没有做作者想要做的事情。
-
它没有坏。它只是有你不喜欢的行为。更改它的问题是它可能会影响向后兼容性。
-
@Gray:他们不应该改变它,而是添加一个带有谓词作为参数的方法并弃用旧的。
标签: java multithreading wait