这里有一个再现:import java.util.concurrent.*;public class Main { public static void main(String[] args) throws ExecutionException, InterruptedException { System.out.println("Hello!"); ExecutorService exec = Executors.newSingleThreadExecutor(); Future<Integer> f = exec.submit(() -> x()); f.get(); System.out.println("f.get() returned"); exec.shutdownNow(); System.out.println("Good bye!"); } private static Integer x() { throw new RuntimeException("An unfortunate event"); }}输出只显示“你好!” 和异常堆栈跟踪,然后让程序永远挂起。下面的更改可以解决该问题,但是知道为什么执行会挂在上面的代码中吗?使用公共线程池不会挂起:Future<Integer> f = ForkJoinPool.commonPool().submit(() -> x());将调用包装在 try/catch 周围可以让应用程序正常退出:Future<Integer> f = exec.submit(() -> x());try { f.get();} catch (Exception ex) { ex.printStackTrace();}
1 回答
桃花长相依
TA贡献1860条经验 获得超8个赞
总是很难找到一个很好的例子try-finally及其适当的用法。我认为是这样。
try {
f.get();
System.out.println("f.get() returned");
} finally {
exec.shutdownNow();
}
抛出的异常f.get();没有处理,主线程失败。但是该应用程序仍然包含ExecutorService您无法直接访问的非守护线程。
添加回答
举报
0/150
提交
取消