Разница в производительности между классом Iterator и конструкцией foreach - PullRequest
4 голосов
/ 06 июля 2010

У меня работает следующий код, но я иногда получаю какое-то исключение параллелизма при его запуске.

ArrayList<Mob> carriers = new ArrayList<Mob>();
ArrayList<Mob> mobs = new ArrayList<Mob>();
...
for (Mob carrier : carriers){
    for (Mob mob : mobs){
        checkInfections (carrier, mob);
    } 
}

Я реорганизовал его для решения проблемы параллелизма, но это привело меня к вопросу. Будет ли разница в производительности, если я изменю конструкцию for на шаблон Iterator? Какая разница в уровне доступа между конструкцией foreach и классом Iterator?

Ответы [ 4 ]

8 голосов
/ 06 июля 2010

Различие в значительной степени синтаксическое, за исключением того, что Iterator может удалять элементы из Collection, который он повторяет. Технически, улучшенные циклы for позволяют вам циклически повторять все, что является Iterable, что включает как минимум Collection s и массивы.

Не беспокойтесь о различиях в производительности. Такая микрооптимизация не имеет никакого значения. Если вам нужно удалить предметы по ходу дела, используйте Iterator. В противном случае for циклы, как правило, используются более просто потому, что они более читабельны, например:

for (String s : stringList) { ... }

против

for (Iterator<String> iter = stringList.iterator(); iter.hasNext(); ) {
  String s = iter.next();
  ...
}
0 голосов
/ 02 июня 2013

Итератор (интерфейс) можно использовать только в коллекциях, таких как List, Set & Queue, но для каждой петли можно использовать все, что можно повторять, например Collections и Array.И для каждого цикла это более читабельно ..

0 голосов
/ 06 июля 2010

"Исключение параллелизма", о котором вы говорите, скорее всего, java.util.ConcurrentModificationException. Вы получаете это, потому что вы не можете изменить список, пока вы перебираете его; если вы это сделаете, итератор заметит и сгенерирует это исключение.

Если вам нужно удалить элементы из списка во время итерации по нему, сделайте это с помощью метода remove() на итераторе, например:

List<String> list = ...; // wherever you get this

for (Iterator<String> iter = list.iterator(); iter.hasNext(); ) {
    String s = iter.next();
    if (...) {
        iter.remove(); // Remove element through iterator
    }
}

(Примечание: в этом случае вы не можете использовать синтаксис foreach для цикла, потому что вам нужен явный доступ к итератору).

0 голосов
/ 06 июля 2010

За кулисами новый стиль for реализован в терминах итераторов компилятором, поэтому не будет никакой разницы, если вы сделаете это самостоятельно.

...