Многопоточный код в Java с ExecutorService не может быть возвращен, почему? - PullRequest
1 голос
/ 01 июля 2011

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

Это простой многопоточный процесс для генерации некоторого результирующего XML для поискового запроса.Результат выполнения этого метода:

Возврат из потоков

Строка System.out.println ("Законченный цикл многопоточности"); "никогда не достигается.

Изменение количества потоков не помогает.

private void fillAllResults() {
        int threads = 2;
        final FutureTask[] tasks = new FutureTask[threads];
        final ExecutorService executor = Executors.newCachedThreadPool();
        for (int i = 0; i < allResults.size(); i++) {
            tasks[i] = new FutureTask<Integer>(new Callable<Integer>() {
                public Integer call() throws Exception {
                    int index;
                    while ((index = getResultsIndex()) < allResults.size()) {
                        System.out.println("Processing result " + index);

                        Result result = allResults.get(index);
                        fillResultXML(result);
                    }
                    System.out.println("Returning from threads");
                    return 1;
                }
            });
            executor.execute(tasks[i]);
        }
        for (int i = 0; i < threads; i++) {
            try {
                tasks[i].get();
            } catch (InterruptedException e) {
                e.printStackTrace();
            } catch (ExecutionException e) {
                e.printStackTrace();
            }
        }
        executor.shutdown();

        System.out.println("Finished multithreading loop");
    }

Редактируйте, спасибо всем за быстрые ответы! Вот ответы:

Показывает «результат обработки» каксколько раз я получаю результаты. Если allResults.size () равен 25, он показывает результат обработки 1, результат обработки 2 ... результат обработки 24.

Вот дополнительный код, который отсутствует:

private List<Result> allResults = new ArrayList<Result>();
private int resultsIndex = 0;

private synchronized int getResultsIndex() {
return resultsIndex++;
}

И в случае, если кому-то интересно, я могу гарантировать, что ни один из кодов в цикле не увеличит размер allResults.

Ответы [ 3 ]

1 голос
/ 01 июля 2011

Я полагаю, это связано с тем, что ваш массив tasks имеет длину threads (т. Е. Два в вашем случае), но вы присваиваете ему больше значений в строках

for (int i = 0; i < allResults.size(); i++) {
    tasks[i] = ...
    ....
}

Если ваш список allResults содержит более двух записей, ваша тема будет остановлена ​​на ArrayIndexOutOfBoundsException. Может быть, вы поймали этот, но не обрабатывали его должным образом вне кода, который вы представили.

0 голосов
/ 01 июля 2011

Из вашего кода непонятно, что такое allResults и getResultsIndex, но вы никогда не обновляете то, что возвращает getResultsIndex.

0 голосов
/ 01 июля 2011

Похоже, что getResultsIndex () не обновляется после каждого цикла, что приводит к бесконечному циклу.

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