Если один поток выдает исключение, то Как остановить другие ожидающие потоки - PullRequest
0 голосов
/ 21 мая 2018

В Java Если у меня три потока t1, t2 и t3 .Предположим, что t1 выполняет какую-то задачу, а t2, t3 находятся в состоянии ожидания.Теперь, если t1 сталкивается / выбрасывает какое-либо исключение, я не хочу выполнять мой поток t2, t3 .

Как мы можем достичь этогофункциональность в Java?

1 Ответ

0 голосов
/ 21 мая 2018

Не используйте потоки напрямую, используйте платформу executor.

В частности, используйте CompletionService, чтобы вы могли извлекать задачи, которые вы отправляете исполнителю, в порядке выполнения (успешно или нет).

Вместо:

Thread t1 = new Thread(() -> { /* runnable 1 */ });
Thread t2 = new Thread(() -> { /* runnable 2 */ });
Thread t3 = new Thread(() -> { /* runnable 3 */ });

Создайте CompletionService:

ExecutorService executor = ...;  // e.g. Executors.newFixedThreadPool
CompletionService completionService = new CompletionService(executor);

Теперь создайте список для хранения Future s, возвращаемых отправкой задач.CompletionService:

List<Future<?>> futures = new ArrayList<>();
futures.add(completionService.submit(() -> { /* runnable 1 */ })); 
futures.add(completionService.submit(() -> { /* runnable 2 */ })); 
futures.add(completionService.submit(() -> { /* runnable 3 */ }));

Теперь используйте take, чтобы получить фьючерсы в порядке завершения:

for (int i = 0; i < futures.size(); ++i) {
  Future<?> completed = futures.take();
  try {
    completed.get();
  } catch (ExecutionException e) {
    // An exception occurred whilst running the task.
    // Cancel all the tasks.
    futures.forEach(f -> f.cancel(true));
  }
}

Конечно, cancel может что-либо сделатьздесь полезно, вам понадобятся ваши runnables для проверки на прерывание;но в любом случае вам понадобятся средства для проверки «сбоя» в других потоках.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...