Java 如果任务遇到异常,将抑制其进一步执行。为什么?
Java 如果任务遇到异常,将抑制其进一步执行。为什么?,java,multithreading,Java,Multithreading,scheduleAtFixedRate和ScheduleAtFixedDelay的文档说明: 如果任务的任何执行遇到异常,则后续 死刑被禁止 假设我的任务设计用于执行某些网络作业,但找不到主机。这些任务不会再次执行吗?主机可能会在下一刻重新联机 假设文档讨论的是RuntimeException的一个实例,比如数组索引越界,那么任务将永远不再执行吗?如果我想让它们继续执行,该怎么办?检查由调度程序执行的Runnable action中的未修补异常。默认情况下,JVM不会捕获它们,线程会在未被注意的
scheduleAtFixedRate
和ScheduleAtFixedDelay
的文档说明:
如果任务的任何执行遇到异常,则后续
死刑被禁止
假设我的任务设计用于执行某些网络作业,但找不到主机。这些任务不会再次执行吗?主机可能会在下一刻重新联机
假设文档讨论的是
RuntimeException
的一个实例,比如数组索引越界,那么任务将永远不再执行吗?如果我想让它们继续执行,该怎么办?检查由调度程序执行的Runnable action中的未修补异常。默认情况下,JVM不会捕获它们,线程会在未被注意的情况下崩溃
我建议使用自定义
ScheduledThreadPoolExecutor
,如下所示:
static class MyScheduledThreadPoolExecutor extends ScheduledThreadPoolExecutor {
public MyScheduledThreadPoolExecutor(int corePoolSize,ThreadFactory threadFactory) {
super(corePoolSize, threadFactory);
}
@Override
public ScheduledFuture<?> schedule(Runnable command, long delay,TimeUnit unit) {
return super.schedule(new SheduleExceptionCatcher(command), delay, unit);
}
@Override
public ScheduledFuture<?> scheduleAtFixedRate(Runnable command,long initialDelay, long period, TimeUnit unit) {
return super.scheduleAtFixedRate(new SheduleExceptionCatcher(command), initialDelay, period, unit);
}
@Override
public ScheduledFuture<?> scheduleWithFixedDelay(Runnable command,long initialDelay, long delay, TimeUnit unit) {
return super.scheduleWithFixedDelay(new SheduleExceptionCatcher(command), initialDelay, delay, unit);
}
/** Wrap for Runnable - for error catching */
private static class SheduleExceptionCatcher implements Runnable {
private Runnable task;
public SheduleExceptionCatcher(Runnable task) {
this.task = task;
}
@Override
public void run() {
try {
task.run();
} catch (Throwable e) {
System.err.println("" + e); // or some logger probably
}
}
}
}
将打印
java.lang.RuntimeException: Test Error
java.lang.RuntimeException: Test Error
java.lang.RuntimeException: Test Error
java.lang.RuntimeException: Test Error
java.lang.RuntimeException: Test Error
因此,尽管存在错误,您的任务仍将永远执行
任务将永远不再执行吗
这就是“后续处决被压制”的意思,不是吗
如果我想让他们继续执行呢
不要让
运行时异常
和错误
从它们中逃脱。当我忘记在可运行
中捕获异常时,不了解崩溃发生在哪里,这非常恼人。事实上,我不需要忽略所有这些异常,我只需要确保我不会忽略它们。为此,我创建了一个类,它是Runnable
的包装器,记录异常并在需要时传播它们:
executorService.submit(new CatchyRunnable(new Runnable() {
@Override
public void run() {
throw new RuntimeException("log me");
}
});
通过应用工厂方法模式,您可以使用更简洁的语法,我正计划与lambdas一起使用:
executorService.submit(new CatchyRunnable(() -> {
throw new RuntimeException("log me");
});
你是在问文档是否存在漏洞?@SLaks-"我是在问,如果我希望线程在异常情况下重新执行,该怎么办?你必须自己实现该功能,然后重试。只需捕获可能的异常并进行一些处理或忽略它。
Runnable#run()
不声明抛出的已检查异常。javadoc引用的是未捕获的未检查异常。只要运行()
正确终止后,ScheduledExecutorService
将继续提交您的Runnable
。您不需要所有这些。只需捕获RuntimeException和Error。一旦您忘记尝试捕获包装,就会对奇怪的代码行为感到困惑。很难找到多线程错误。而且您也无法我不能理解你的第一句话的头尾,但是你写的代码越多,你的同事就越不用,你依赖他们的理由就越少。你不能用额外的软件工程来解决社会问题,不管它多么巧妙。一个未捕获的例外是代码中未定义状态的一个标志at Java则会抑制任何进一步的异常,这是为了防止损害。@Two Java不会“抑制进一步的异常”。它会抑制进一步的执行。
executorService.submit(new CatchyRunnable(() -> {
throw new RuntimeException("log me");
});