我的代码是这样的:ScheduledExecutorService executor = Executors.newScheduledThreadPool(8);//complex code that call this multiple times too add tasks:executor.schedule(() -> { doRealTask(); }, 0, TimeUnit.MICROSECONDS);//drain the pool on some condition, e.g. meets tasks that can't be parallelized:executor.shutdown();//without this, awaitTermination won't return since all the threads in the pool will be paused, not terminatedexecutor.awaitTermination(1000000, TimeUnit.SECONDS);//continue to add more tasks:executor.schedule(...);最后一个代码抛出 java.util.concurrent.RejectedExecutionException 。原因似乎是执行器已关闭。但没有“startAgain”功能。显然创建一个新的 ScheduledExecutorService 是有效的,但我觉得我使用了错误的解决方案。如何在Java中实现这个?
2 回答

三国纷争
TA贡献1804条经验 获得超7个赞
将您的 future 存储在列表中,然后使用 get 有效地加入。
List<Future<?>> futures = new ArrayList<>();
futures.add(executor.schedule(() -> { doRealTask(); }, 0, TimeUnit.MICROSECONDS));
而不是关闭。
for(Future<?> future: futures){
future.get();
}
futures.clear();
现在您需要处理异常,并且可能在获取时包含超时。

心有法竹
TA贡献1866条经验 获得超5个赞
关闭状态是不可逆的,因此如果需要,只需创建一个新的执行器即可。没有其他方法可以重用之前的方法。但是,如果您要再次创建它,为什么需要关闭它呢?如果它有太多任务,并且您可以牺牲它们来换取新任务,那么为每个任务配置合理的超时并配置池本身(例如池和任务队列大小)是有意义的。
每次调用Executor.schedule(() -> { doRealTask(); }, 0, TimeUnit.MICROSECONDS);
都会返回ScheduledFuture
实例,您可以存储它并稍后处理结果。
添加回答
举报
0/150
提交
取消