我正在尝试学习 java 并发 API,并且为了我的练习,我想安排一个作业每隔 X 秒定期运行一次。该作业将计算一个随机数。
我想在定时任务完成后第一时间得到结果。 我无法仅使用 API 完成此操作,所以我破解了它。
有没有办法在不使用低级机制的情况下做得更好?
我希望能够删除 MyRandomGiverTask.getResult()
中的同步,而是使用
类似于 ScheduledFuture.get()
。但是在我的代码中,ScheduledFuture 从未完成/完成。
这是我目前的解决方案:
class A {
public static void main() {
MyRandomGiverTask task = new MyRandomGiverTask(200);
ScheduledExecutorService scheduler = Executors.newScheduledThreadPool(1);
ScheduledFuture<Double> scheduledDouble =
(ScheduledFuture<Double>) scheduler
.scheduleAtFixedRate(task, 1, 4, TimeUnit.SECONDS);
while (true) {
System.out.println(" >> " + task.getResult());
}
}
public class MyRandomGiverTask implements Runnable {
MyRandomGiver giver = new MyRandomGiver();
int param;
double result;
public MyRandomGiverTask(int param) { this.param = param; }
@Override public void run() { result = giver.getRandom(param); }
public double getResult() {
try {
while (result == 0d) {
try {
Thread.sleep(500);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
return result;
} finally {
result = 0d;
}
}
}
}
最佳答案
您的任务按固定速率安排。这意味着在您取消任务之前,它会由执行者以固定的速率一次又一次地执行。这样的任务唯一能做的就是产生副作用。它不能返回任何东西,因为执行者返回的 future 代表任务的所有未决执行。顺便说一句,您会注意到 schedule
方法采用 Callable 作为参数(这可能会产生一些结果),而 sceduleAtFixedRate
方法仅采用 Runnable 作为参数(返回 void ,因此不能返回任何东西)。
所以,如果你想打印每次执行的结果,那么简单地让任务本身(Runnable)打印它的结果,或者让 runnable 把它的结果放在一个阻塞队列中,并让主线程 从队列中取出
。主线程将因此被阻塞,直到一些结果被放入队列。
关于java - 获取定时任务的结果,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8869870/