Почему для массивов работают циклы for-each? (Java) - PullRequest
3 голосов
/ 16 июня 2020

Я не понимаю, как a для каждого l oop может перебирать массив в Java. Я понимаю, что для каждого цикла можно выполнять итерацию, хотя любой класс, реализующий интерфейс Iterable, но массивы в Java не реализуют Iterable, поэтому как возможно использовать для каждого l oop на них?

Ответы [ 2 ]

4 голосов
/ 16 июня 2020

Если правая часть идиомы for (:) - это array, а не объект Iterable, внутренний код использует счетчик индекса int и проверяет вместо него array.length. Поэтому его можно использовать для l oop через массивы. Подробнее см. Java Спецификацию языка .

Часть этого ответа была исключена из здесь . Вы также можете взглянуть на этот вопрос.

Я хотел бы добавить, если вы хотите, вы можете легко преобразовать java array в Iterable:

Integer arr[] = { 1, 2, 3, 4, 5};

List<Integer> list = Arrays.asList(arr);
// or
Iterable<Integer> iterable = Arrays.asList(arr);
2 голосов
/ 16 июня 2020

Согласно JLS :

Расширенный оператор for имеет форму:

EnhancedForStatement: for ({VariableModifier} UnannType VariableDeclaratorId: Expression) Statement

EnhancedForStatementNoShortIf: for ({VariableModifier} UnannType VariableDeclaratorId: Expression) StatementNoShortIf

Java foreach l oop или расширенный оператор for переводится в оператор basi * 1037 следующим образом:

  1. Если тип Expression является подтипом Iterable<X> для некоторого аргумента типа X, тогда пусть I будет типом java.util.Iterator<X>; в противном случае, пусть I будет необработанный тип java.util.Iterator.

Расширенный оператор for эквивалентен оператору basi c for в форме:

for (I #i = Expression.iterator(); #i.hasNext(); ) {
    {VariableModifier} TargetType Identifier =
        (TargetType) #i.next();
    Statement
}
В противном случае Expression обязательно имеет тип массива, T[].

Расширенный оператор for эквивалентен оператору basi c for в форме:

T[] #a = Expression;
L1: L2: ... Lm:
for (int #i = 0; #i < #a.length; #i++) {
    {VariableModifier} TargetType Identifier = #a[#i];
    Statement
}
...