В том, какие случаи делают Future.get () бросают ExecutionException или InterruptedException

Мой фрагмент кода:

ExecutorService executor = Executors.newSingleThreadExecutor();
try {
    Task t = new Task(response,inputToPass,pTypes,unit.getInstance(),methodName,unit.getUnitKey());
    Future<SCCallOutResponse> fut = executor.submit(t);
    response = fut.get(unit.getTimeOut(),TimeUnit.MILLISECONDS);
} catch (TimeoutException e) {
    // if the task is still running, a TimeOutException will occur while fut.get()
    cat.error("Unit " + unit.getUnitKey() + " Timed Out");
    response.setVote(SCCallOutConsts.TIMEOUT);
} catch (InterruptedException e) {
    cat.error(e);
} catch (ExecutionException e) {
    cat.error(e);
} finally {
    executor.shutdown();
}

Как я должен обработать InterruptedException и ExecutionException в коде?

И в том, какие случаи, эти исключения выдаются?

25
задан Ravindra babu 5 July 2016 в 14:39
поделиться

3 ответа

ExecutionException и InterruptedException - две очень разные вещи.

ExecutionException обертывает любое исключение, сгенерированное выполняемым потоком, поэтому, если ваш поток, например, выполнял какой-то ввод-вывод, который вызвал выброс IOException , это было бы заключено в ExecutionException и повторно.

InterruptedException не является признаком того, что что-то пошло не так. Он предназначен для того, чтобы дать вам возможность сообщить вашим потокам, когда пришло время остановиться, чтобы они могли завершить свою текущую работу и корректно выйти. Скажем, я хочу, чтобы мое приложение перестало работать, но я не хочу, чтобы мои потоки теряли то, что они делают, посреди чего-то (что бы произошло, если бы я сделал их потоками-демонами). Поэтому, когда приложение завершает работу, мой код вызывает метод прерывания для этих потоков, который устанавливает для них флаг прерывания, и в следующий раз, когда эти потоки ожидают или спят, они проверяют флаг прерывания и генерируют исключение InterruptedException , который я могу использовать для выхода из любой логики обработки / ожидания с бесконечным циклом, в которой задействованы потоки. (И если поток не ждет или не спит, он может просто периодически проверять флаг прерывания.) Так что это экземпляр исключения, используемого для изменения логического потока. Единственная причина, по которой вы вообще это должны регистрировать, - это пример программы, чтобы показать вам, что происходит, или если вы отлаживаете проблему, при которой логика прерывания работает неправильно.

39
ответ дан 28 November 2019 в 20:51
поделиться

InterruptedException будет сгенерировано, если прерывание вызывается в ожидающем потоке до завершения вычисления.

ExecutionException будет сгенерировано, если задействованное вычисление (в данном случае Task ) выдает исключение само.

Как вы хотите справиться с этим, полностью зависит от вашего приложения.

РЕДАКТИРОВАТЬ: Вот демонстрация прерывания:

import java.util.concurrent.*;

public class Test
{
    public static void main(String[] args) throws Exception
    {
        ExecutorService executor = Executors.newFixedThreadPool(2);
        Future<String> future = executor.submit(new SlowCallable());
        executor.submit(new Interruptor(Thread.currentThread()));
        try
        {
            System.out.println(future.get());
        }
        catch (InterruptedException e)
        {
            System.out.println("I was interrupted");
        }
    }

    private static class Interruptor implements Callable<String>
    {
        private final Thread threadToInterrupt;

        Interruptor(Thread threadToInterrupt)
        {
            this.threadToInterrupt = threadToInterrupt;
        }

        public String call() throws Exception
        {
            Thread.sleep(2000);
            threadToInterrupt.interrupt();
            return "interrupted other thread";
        }
    }

    private static class SlowCallable implements Callable<String>
    {
        public String call() throws Exception
        {
            Thread.sleep(5000);
            return "finished";
        }
    }
}
7
ответ дан 28 November 2019 в 20:51
поделиться

В статье IBM Developer Works Работа с InterruptedException есть несколько советов по обработке InterruptedException .

3
ответ дан 28 November 2019 в 20:51
поделиться
Другие вопросы по тегам:

Похожие вопросы: