【问题标题】:Java: ExecutorService and Callables, unable to catch exceptionJava:ExecutorService 和 Callables,无法捕获异常
【发布时间】:2016-04-13 22:50:26
【问题描述】:

我试图弄清楚为什么下面的代码在我运行时没有打印出 NumberFormatException 的堆栈跟踪?

我不确定以这种方式使用 callables 和 ExecutorService 是否很常见,我用谷歌搜索并找不到解决我的问题的方法......可能有一些我没有看到的非常明显的东西。

import java.util.ArrayList;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

public class CallablesTest {

    private final static ArrayList<Callable<Void>> mCallables = new ArrayList<>();
    private final static ExecutorService mExecutor = Executors.newFixedThreadPool(4);

    public static void main(String[] args) throws Exception{
        testMethod();
    }

    static void testMethod() throws Exception {

        mCallables.clear();

        for(int i=0; i<4; i++){
            mCallables.add(new Callable<Void>() {

                @Override
                public Void call() throws Exception {
                    //if (Thread.currentThread().isInterrupted()) {
                    //    throw new InterruptedException("Interruption");
                    //}
                    System.out.println("New call");
                    Double.parseDouble("a");

                    return null;
                } //end call method

            }); //end callable anonymous class
        }
        try {
            mExecutor.invokeAll(mCallables);
            mExecutor.shutdown();
        } catch (Exception e) {
          e.printStackTrace();
        }
    }
}

【问题讨论】:

  • 您的代码中目前没有任何部分会引发NumberFormatException。 ExecutorService 不会直接暴露异步运行 Callables 抛出的异常。
  • 对不起,代码有错误。现在应该有一个 NumberFormatException 。虽然我不理解您的评论“ExecutorService 不会直接暴露异步运行的 Callables 引发的异常。”
  • ExecutorService 的要点通常用作线程池,因此在不同的线程上执行您的Callable(s)。如果您的Callable 的执行在其他线程之一中引发异常,则ExecutorService 不会(默认情况下)拦截它。它只是丢弃它。这一切都可以配置,看ThreadPoolExecutor。

标签: java executorservice callable


【解决方案1】:

我想我可能已经找到了我自己的问题的答案...如果您从 ExecutorService.invokeAll...捕捉异常

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;

public class ThreadTest {

    private final static ArrayList<Callable<Boolean>> mCallables = new ArrayList<>();
    private final static ExecutorService mExecutor = Executors.newFixedThreadPool(4);

    public static void main(String[] args) throws Exception{
        testMethod();
    }

    static void testMethod() throws Exception {

        mCallables.clear();

        for(int i=0; i<4; i++){
            mCallables.add(new Callable<Boolean>() {

                @Override
                public Boolean call() throws Exception {
                    //if (Thread.currentThread().isInterrupted()) {
                    //    throw new InterruptedException("Interruption");
                    //}
                    System.out.println("New call");

                    double d = Double.parseDouble("a");

                    return true;
                } //end call method

            }); //end callable anonymous class
        }
        try {
            List<Future<Boolean>> f= mExecutor.invokeAll(mCallables);
            f.get(1).get();
            f.get(2).get();
            f.get(3).get();
            f.get(0).get();

        } catch (Exception e) {
            String s = e.toString();
            System.out.println(s);
        }

        mExecutor.shutdown();
    }
}

【讨论】:

    猜你喜欢
    • 2016-08-09
    • 2010-10-29
    • 1970-01-01
    • 2021-10-09
    • 2021-09-17
    • 2021-10-03
    • 2018-02-04
    • 2018-02-04
    相关资源
    最近更新 更多