【发布时间】:2012-01-19 08:48:21
【问题描述】:
我有一个从 Runnable 实现的轮询器。轮询器将自身传递给 ScheduledExecutorService。由于我需要根据任务不同的延迟时间,所以我使用'schedule'而不是'scheduleWithFixedDelay',这有问题......
很遗憾,此轮询器无法正常关闭...
日志显示: 一开始,“主”线程调度一个轮询器; 之后,“poller18”(或任何线程 ID)线程调度以下轮询器。
当被摧毁时, 'main'线程调用destroy,设置flag为true,然后调用poller.shutdown; 但是 'poller18' 线程永远不会看到该标志(在 schedulePoller 中始终为 false),因此它将继续调度下一个轮询器。
我的问题是: 1. isShuttingDown 是类中的私有字段。我认为它将由线程共享,因为它不是 ThreadLocal。为什么不是? 2.在这种情况下,有没有其他方法可以通知poller18 poller正在关闭?
class Poller implements Runnable {
private boolean isShuttingDown = false;
private ScheduledExecutorService poller = null;
@PostConstruct
protected synchronized void start() {
if (enabled && poller == null) {
poller = Executors.newScheduledThreadPool(1);
schedulePoller(1);
}
}
protected synchronized void schedulePoller(final long period) {
if (poller() == null || poller().isShutdown() || this.isShuttingDown) {
return;
}
LOGGER.info("schedule a new poller");
poller().schedule(this,
period,
TimeUnit.MILLISECONDS);
}
public void run() {
... do work ...
if (more work)
schedulePoller(1);
else
schedulePoller(10);
}
public void destroy() {
this.isShuttingDown = true;
poller.shutdown();
while (!poller.awaitTermination(SHUTDOWN_WAIT_SECONDS, TimeUnit.SECONDS)) {
LOGGER.info("Waiting for remaining tasks to finish.");
poller.shutdown();
}
LOGGER.info("All remaining tasks have finished.");
}
}
在 spring 配置中,我将 destroy_method 设置为 destroy()。
非常感谢!如果我的描述中有任何混淆,请告诉我。
【问题讨论】:
标签: java runnable executorservice