2

我有一个提交给ExecutorService. 但是我需要在凌晨 2:30 的最后期限之前关闭 ExecutorService,即使任务没有完成。我怎样才能做到这一点?我检查了API,只有一个方法如下:

ExecutorService exec = //...    
exec.awaitTermination(100, TimeUnit.MILLISECONDS);

但是我怎样才能使下面的块原子地执行呢?也就是说,我怎样才能避免差距?例如:

long timeDiff= calculate(now, deadline);
// Gap: assuming current thread does not have chance to run for 10 minutes...
exec.awaitTermination(timeDiff, TimeUnit.MILLISECONDS);

谢谢。

4

2 回答 2

2

您可能不是指“原子地”,我认为您的意思是“毫不拖延”。所以timeDiff调用时仍然是正确的exec.awaitTermination()

我认为这是正确的,所以答案是:你不能

如果您对细节感兴趣:您的 Java 代码被翻译成 Java 字节码,这些由 JVM 执行,JVM 是在您的操作系统上运行的常规进程。而且您根本无法阻止操作系统中断线程(我假设您使用具有抢先式多任务处理的操作系统(每个 UNIX(包括 Linux 和 Mac OS X)、Windows 95 或更高版本……))。

即使您可以在一个 Java 字节码中完成所有这些操作,它仍然无法按照您的意愿工作,因为操作系统可能会在一个 Java 字节码的中间打断您。

即使是一种awaitTermination(Date deadline)方法也无济于事。它也必须由某人实施。

你能做的最好的事情就是用尽可能少的字节码来做。

如果我是你,我可能会像你的代码那样做。

但是,这可能更精确一点:

Date deadline = ....;

final TimerTask stopTask = new TimerTask() {
    public void run() {
        exec.shutdownNow();
    }
};

new Timer().schedule(stopTask, deadline);

但正如我所说:没有真正的保证shotdownNow()会立即在deadline. 实际上,设置deadline为实际截止日期前一秒应该没问题:-)

于 2011-08-23T18:16:54.307 回答
1

在另一个高优先级线程(或计时器)中等待截止日期并调用exec.shutdownNow()

于 2011-08-23T17:46:32.770 回答