usar - while do while em java




Como funciona o laço Java 'for each'? (18)

A construção de cada também é válida para matrizes. por exemplo

String[] fruits = new String[] { "Orange", "Apple", "Pear", "Strawberry" };

for (String fruit : fruits) {
    // fruit is an element of the `fruits` array.
}

que é essencialmente equivalente de

for (int i = 0; i < fruits.length; i++) {
    String fruit = fruits[i];
    // fruit is an element of the `fruits` array.
}

Então, resumo geral:
[nsayer] O seguinte é a forma mais longa do que está acontecendo:

for(Iterator<String> i = someList.iterator(); i.hasNext(); ) {
  String item = i.next();
  System.out.println(item);
}

Note que se você precisar usar i.remove (); em seu loop, ou acessa o iterador real de alguma forma, você não pode usar o idioma for (:), uma vez que o iterador real é meramente inferido.

[Denis Bueno]

Está implícito na resposta do nsayer, mas vale notar que a sintaxe do OP para (..) funcionará quando "someList" for qualquer coisa que implemente java.lang.Iterable - não precisa ser uma lista, ou alguma coleção de java.util. Mesmo seus próprios tipos, portanto, podem ser usados ​​com esta sintaxe.

Considerar:

List<String> someList = new ArrayList<String>();
// add "monkey", "donkey", "skeleton key" to someList
for (String item : someList) {
    System.out.println(item);
}

Como seria o equivalente for loop sem usar o para cada sintaxe?


A construção de loop Java "for-each" permitirá a iteração em dois tipos de objetos:

  • T[] (matrizes de qualquer tipo)
  • java.lang.Iterable<T>

A interface Iterable<T> tem apenas um método: Iterator<T> iterator() . Isso funciona em objetos do tipo Collection<T> porque a interface Collection<T> estende Iterable<T> .


Aqui está uma expressão equivalente.

for(Iterator<String> sit = someList.iterator(); sit.hasNext(); ) {
    System.out.println(sit.next());
}

Aqui está uma resposta que não pressupõe o conhecimento dos Iteradores Java. É menos preciso, mas é útil para a educação.

Enquanto programamos, frequentemente escrevemos códigos parecidos com os seguintes:

char[] grades = ....
for(int i = 0; i < grades.length; i++) {   // for i goes from 0 to grades.length
    System.out.print(grades[i]);           // Print grades[i]
}

A sintaxe foreach permite que esse padrão comum seja escrito de uma maneira mais natural e menos sintaticamente barulhenta.

for(char grade : grades) {   // foreach grade in grades
    System.out.print(grade); // print that grade
}

Além disso, essa sintaxe é válida para objetos como Listas ou Conjuntos que não suportam a indexação de matrizes, mas que implementam a interface Java Iterable.


Conforme definido no JLS for-each, o loop pode ter duas formas:

  1. Se o tipo de expressão for um subtipo de Iterable , a tradução será como:

    List<String> someList = new ArrayList<String>();
    someList.add("Apple");
    someList.add("Ball");
    for (String item : someList) {
        System.out.println(item);
    }
    
    // IS TRANSLATED TO:
    
    for(Iterator<String> stringIterator = someList.iterator(); stringIterator.hasNext(); ) {
        String item = stringIterator.next();
        System.out.println(item);
    }
  2. Se a Expressão tiver necessariamente um tipo de matriz T[] então:

    String[] someArray = new String[2];
    someArray[0] = "Apple";
    someArray[1] = "Ball";
    
    for(String item2 : someArray) {
        System.out.println(item2);
    }
    
    // IS TRANSLATED TO:
    for (int i = 0; i < someArray.length; i++) {
        String item2 = someArray[i];
        System.out.println(item2);
    }

O Java 8 introduziu fluxos que geralmente funcionam melhor. Nós podemos usá-los como:

someList.stream().forEach(System.out::println);
Arrays.stream(someArray).forEach(System.out::println);

Ele adiciona beleza ao seu código, removendo toda a confusão básica de loop. Ele dá uma aparência limpa ao seu código, justificado abaixo.

Normal for loop:

void cancelAll(Collection<TimerTask> list) {
    for (Iterator<TimerTask> i = list.iterator(); i.hasNext();)
         i.next().cancel();
}

Usando for-each:

void cancelAll(Collection<TimerTask> list) {
    for (TimerTask t : list)
        t.cancel();
}

for-each é um constructo sobre uma coleção que implementa o Iterator . Lembre-se que sua coleção deve implementar o Iterator ; caso contrário, você não poderá usá-lo para cada um.

A seguinte linha é lida como " para cada TimerTask t na lista " .

for (TimerTask t : list)

Há menos chance de erros no caso de for-each. Você não precisa se preocupar em inicializar o iterador ou inicializar o contador de loops e finalizá-lo (onde há espaço para erros).


Isso parece loucura, mas ei, funciona

List<String> someList = new ArrayList<>(); //has content
someList.forEach(System.out::println);

Isso funciona. Magia


No Java 8, eles foram introduzidos para o Eee. Usando a lista, os mapas podem ser colocados em loop.

Repetir uma lista usando para cada

List<String> someList = new ArrayList<String>();
someList.add("A");
someList.add("B");
someList.add("C");

someList.forEach(listItem -> System.out.println(listItem))

ou

someList.forEach(listItem-> {
     System.out.println(listItem); 
});

Loop um mapa usando para cada

Map<String, String> mapList = new HashMap<>();
    mapList.put("Key1", "Value1");
    mapList.put("Key2", "Value2");
    mapList.put("Key3", "Value3");

mapList.forEach((key,value)->System.out.println("Key: " + key + " Value : " + value));

ou

mapList.forEach((key,value)->{
    System.out.println("Key : " + key + " Value : " + value);
});

O docs.oracle.com/javase/1.5.0/docs/guide/language/foreach.html , adicionado no Java 5 (também chamado de "enhanced for loop"), é equivalente a usar um java.util.Iterator --it é um açúcar sintático para a mesma coisa. Portanto, ao ler cada elemento, um por um e em ordem, um foreach sempre deve ser escolhido sobre um iterador, pois é mais conveniente e conciso.

para cada

for(int i : intList) {
   System.out.println("An element in the list: " + i);
}

Iterador

Iterator<Integer> intItr = intList.iterator();
while(intItr.hasNext()) {
   System.out.println("An element in the list: " + intItr.next());
}

Há situações em que você deve usar um Iterator diretamente. Por exemplo, tentar excluir um elemento ao usar um foreach pode (será?) Resultar em um ConcurrentModificationException .

foreach vs. for : diferenças básicas

A única diferença prática entre for e foreach é que, no caso de objetos indexáveis, você não tem acesso ao índice. Um exemplo de quando o loop básico é necessário:

for(int i = 0; i < array.length; i++) {
   if(i < 5) {
      // Do something special
   }  else {
      // Do other stuff
   }
}

Embora você possa criar manualmente uma variável int de índice separada com foreach ,

int idx = -1;
for(int i : intArray) {
   idx++;
   ...
}

não é recomendado, pois o variable-scope não é o ideal, e o loop básico é simplesmente o formato padrão e esperado para este caso de uso.

foreach vs. for : Performance

Ao acessar coleções, um foreach é significativamente mais rápido que o básico for o acesso ao array do loop. Ao acessar arrays, no entanto - pelo menos com matrizes primitivas e wrapper - o acesso via índices é dramaticamente mais rápido.

Temporizando a diferença entre o acesso ao iterador e ao índice para matrizes int primitivas

Os índices são de 23 a 40 % mais rápidos que os iteradores ao acessar arrays int ou Integer . Aqui está a saída da classe de teste na parte inferior desta postagem, que soma os números em uma matriz int primitiva de 100 elementos (A é iterador, B é índice):

[C:\java_code\]java TimeIteratorVsIndexIntArray 1000000
Test A: 358,597,622 nanoseconds
Test B: 269,167,681 nanoseconds
B faster by 89,429,941 nanoseconds (24.438799231635727% faster)

[C:\java_code\]java TimeIteratorVsIndexIntArray 1000000
Test A: 377,461,823 nanoseconds
Test B: 278,694,271 nanoseconds
B faster by 98,767,552 nanoseconds (25.666236154695838% faster)

[C:\java_code\]java TimeIteratorVsIndexIntArray 1000000
Test A: 288,953,495 nanoseconds
Test B: 207,050,523 nanoseconds
B faster by 81,902,972 nanoseconds (27.844689860906513% faster)

[C:\java_code\]java TimeIteratorVsIndexIntArray 1000000
Test A: 375,373,765 nanoseconds
Test B: 283,813,875 nanoseconds
B faster by 91,559,890 nanoseconds (23.891659337194227% faster)

[C:\java_code\]java TimeIteratorVsIndexIntArray 1000000
Test A: 375,790,818 nanoseconds
Test B: 220,770,915 nanoseconds
B faster by 155,019,903 nanoseconds (40.75164734599769% faster)

[C:\java_code\]java TimeIteratorVsIndexIntArray 1000000
Test A: 326,373,762 nanoseconds
Test B: 202,555,566 nanoseconds
B faster by 123,818,196 nanoseconds (37.437545972215744% faster)

Eu também corri isso para uma matriz Integer , e os índices ainda são o vencedor claro, mas apenas entre 18 e 25 por cento mais rápido.

Para coleções, os iteradores são mais rápidos que os índices

Para uma List de Integers , no entanto, os iteradores são o vencedor claro. Basta alterar o array int na classe de teste para:

List<Integer> intList = Arrays.asList(new Integer[] {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100});

E faça as alterações necessárias na função de teste ( int[] para List<Integer> , length para size() , etc.):

[C:\java_code\]java TimeIteratorVsIndexIntegerList 1000000
Test A: 3,429,929,976 nanoseconds
Test B: 5,262,782,488 nanoseconds
A faster by 1,832,852,512 nanoseconds (34.326681820485675% faster)

[C:\java_code\]java TimeIteratorVsIndexIntegerList 1000000
Test A: 2,907,391,427 nanoseconds
Test B: 3,957,718,459 nanoseconds
A faster by 1,050,327,032 nanoseconds (26.038700083921256% faster)

[C:\java_code\]java TimeIteratorVsIndexIntegerList 1000000
Test A: 2,566,004,688 nanoseconds
Test B: 4,221,746,521 nanoseconds
A faster by 1,655,741,833 nanoseconds (38.71935684115413% faster)

[C:\java_code\]java TimeIteratorVsIndexIntegerList 1000000
Test A: 2,770,945,276 nanoseconds
Test B: 3,829,077,158 nanoseconds
A faster by 1,058,131,882 nanoseconds (27.134122749113843% faster)

[C:\java_code\]java TimeIteratorVsIndexIntegerList 1000000
Test A: 3,467,474,055 nanoseconds
Test B: 5,183,149,104 nanoseconds
A faster by 1,715,675,049 nanoseconds (32.60101667104192% faster)

[C:\java_code\]java TimeIteratorVsIndexIntList 1000000
Test A: 3,439,983,933 nanoseconds
Test B: 3,509,530,312 nanoseconds
A faster by 69,546,379 nanoseconds (1.4816434912159906% faster)

[C:\java_code\]java TimeIteratorVsIndexIntList 1000000
Test A: 3,451,101,466 nanoseconds
Test B: 5,057,979,210 nanoseconds
A faster by 1,606,877,744 nanoseconds (31.269164666060377% faster)

Em um teste eles são quase equivalentes, mas com coleções, o iterador ganha.

* Esta postagem é baseada em duas respostas que escrevi no :

Mais algumas informações: Qual é mais eficiente, um loop for-each ou um iterador?

A classe de teste completa

Eu criei esta classe de comparação-o-tempo-leva-para-fazer-qualquer-coisa depois de ler esta pergunta no :

import  java.text.NumberFormat;
import  java.util.Locale;

/**
   &lt;P&gt;{@code java TimeIteratorVsIndexIntArray 1000000}&lt;/P&gt;

   @see  &lt;CODE&gt;&lt;A HREF=&quot;https://.com/questions/180158/how-do-i-time-a-methods-execution-in-java&quot;&gt;https://.com/questions/180158/how-do-i-time-a-methods-execution-in-java&lt;/A&gt;&lt;/CODE&gt;
 **/
public class TimeIteratorVsIndexIntArray {

    public static final NumberFormat nf = NumberFormat.getNumberInstance(Locale.US);

    public static final void main(String[] tryCount_inParamIdx0) {
        int testCount;

        // Get try-count from a command-line parameter
        try {
           testCount = Integer.parseInt(tryCount_inParamIdx0[0]);
        }
        catch(ArrayIndexOutOfBoundsException | NumberFormatException x) {
           throw  new IllegalArgumentException("Missing or invalid command line parameter: The number of testCount for each test. " + x);
        }

        //Test proper...START
        int[] intArray = new int[] {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100};

        long lStart = System.nanoTime();
        for(int i = 0; i < testCount; i++) {
           testIterator(intArray);
        }

        long lADuration = outputGetNanoDuration("A", lStart);

        lStart = System.nanoTime();
        for(int i = 0; i < testCount; i++) {
           testFor(intArray);
        }

        long lBDuration = outputGetNanoDuration("B", lStart);

        outputGetABTestNanoDifference(lADuration, lBDuration, "A", "B");
    }

    private static final void testIterator(int[] int_array) {
       int total = 0;
       for(int i = 0; i < int_array.length; i++) {
          total += int_array[i];
       }
    }

    private static final void testFor(int[] int_array) {
       int total = 0;
       for(int i : int_array) {
          total += i;
       }
    }
    //Test proper...END

    //Timer testing utilities...START
    public static final long outputGetNanoDuration(String s_testName, long l_nanoStart) {
        long lDuration = System.nanoTime() - l_nanoStart;
        System.out.println("Test " + s_testName + ": " + nf.format(lDuration) + " nanoseconds");
        return  lDuration;
    }

    public static final long outputGetABTestNanoDifference(long l_aDuration, long l_bDuration, String s_aTestName, String s_bTestName) {
        long lDiff = -1;
        double dPct = -1.0;
        String sFaster = null;
        if(l_aDuration > l_bDuration) {
            lDiff = l_aDuration - l_bDuration;
            dPct = 100.00 - (l_bDuration * 100.0 / l_aDuration + 0.5);
            sFaster = "B";
        }
        else {
            lDiff = l_bDuration - l_aDuration;
            dPct = 100.00 - (l_aDuration * 100.0 / l_bDuration + 0.5);
            sFaster = "A";
        }
        System.out.println(sFaster + " faster by " + nf.format(lDiff) + " nanoseconds (" + dPct + "% faster)");
        return  lDiff;
   }

   //Timer testing utilities...END

}

O Java para cada loop (também conhecido como enhanced for loop) é uma versão simplificada de um loop for. A vantagem é que há menos código para escrever e menos variáveis ​​para gerenciar. A desvantagem é que você não tem controle sobre o valor da etapa e nenhum acesso ao índice de loop dentro do corpo do loop.

Eles são melhor usados ​​quando o valor da etapa é um incremento simples de 1 e quando você só precisa acessar o elemento de loop atual. Por exemplo, se você precisar fazer um loop em todos os elementos de uma matriz ou Coleção sem espiar para frente ou para trás do elemento atual.

Não há inicialização de loop, nenhuma condição booleana e o valor da etapa é implícito e é um incremento simples. É por isso que eles são considerados muito mais simples que os loops regulares.

Os loops aprimorados seguem esta ordem de execução:

1) corpo do laço

2) repita desde o passo 1 até todo o array ou coleção ter sido percorrido

Exemplo - Integer Array

int [] intArray = {1, 3, 5, 7, 9};
for(int currentValue : intArray) {
  System.out.println(currentValue);
}

A variável currentValue mantém o valor atual em loop na matriz intArray. Observe que não há valor de etapa explícito - é sempre um incremento de 1.

O cólon pode ser pensado para significar "in". Portanto, a declaração aprimorada para loop declara: faça um loop sobre intArray e armazene o valor int da matriz atual na variável currentValue.

Saída:

1
3
5
7
9

Exemplo - Matriz de Cadeia

Podemos usar o loop for-each para iterar em uma matriz de strings. A declaração de loop informa: loop sobre array de String de myStrings e armazena o valor atual de String na variável currentString.

String [] myStrings  = {
  "alpha",
  "beta",
  "gamma",
  "delta"
};

for(String currentString : myStrings) {
  System.out.println(currentString);
}

Saída:

alpha
beta
gamma
delta

Exemplo - lista

O loop for aprimorado também pode ser usado para iterar em um java.util.List da seguinte maneira:

List<String> myList = new ArrayList<String>();
myList.add("alpha");
myList.add("beta");
myList.add("gamma");
myList.add("delta");

for(String currentItem : myList) {
  System.out.println(currentItem);
}

A declaração de loop informa: faça loop sobre myList List of Strings e armazene o valor atual de List na variável currentItem.

Saída:

alpha
beta
gamma
delta

Exemplo - Set

O loop for aprimorado também pode ser usado para iterar em um java.util.Set da seguinte maneira:

Set<String> mySet = new HashSet<String>();
mySet.add("alpha");
mySet.add("alpha");
mySet.add("beta");
mySet.add("gamma");
mySet.add("gamma");
mySet.add("delta");

for(String currentItem : mySet) {
  System.out.println(currentItem);
}

A declaração de loop informa: faça um loop sobre mySet Set of Strings e armazene o valor atual de Set na variável currentItem. Observe que, como este é um conjunto, os valores de sequência duplicados não são armazenados.

Saída:

alpha
delta
beta
gamma

Fonte: Loops em Java - Ultimate Guide


O conceito de um loop foreach, como mencionado na Wikipedia, é destacado abaixo:

Diferentemente de outras construções de loop for, no entanto, os loops foreach geralmente não mantêm um contador explícito : eles basicamente dizem "faça isso para tudo neste conjunto", em vez de "fazer x vezes". Isso evita possíveis erros "off-by-one" e simplifica a leitura do código.

Portanto, o conceito de um loop foreach descreve que o loop não usa nenhum contador explícito, o que significa que não há necessidade de usar índices para percorrer na lista, portanto, ele salva o erro do usuário off-by-one. Para descrever o conceito geral desse erro off-by-one, vamos pegar um exemplo de um loop para percorrer em uma lista usando índices.

// In this loop it is assumed that the list starts with index 0
for(int i=0; i<list.length; i++){

}

Mas suponha que se a lista começar com o índice 1, então este loop lançará uma exceção, pois não encontrará nenhum elemento no índice 0 e esse erro é chamado de erro off-by-one. Portanto, para evitar esse erro off-by-one, o conceito de loop foreach é usado. Pode haver outras vantagens também, mas isso é o que eu acho que é o principal conceito e a vantagem de usar um loop foreach.


O loop for-each em Java usa o mecanismo do iterador subjacente. Então, é idêntico ao seguinte:

Iterator<String> iterator = someList.iterator();

while (iterator.hasNext()) {
  String item = iterator.next();
  System.out.println(item);
}

Seria algo como isto. Muito crufty.

for (Iterator<String> i = someList.iterator(); i.hasNext(); )
        System.out.println(i.next());

Há um bom writeup para cada um na documentação da Sun.


Uma alternativa para forEach, a fim de evitar o seu "para cada":

List<String> someList = new ArrayList<String>();

Variante 1 (simples):

someList.stream().forEach(listItem -> {
    System.out.println(listItem);
});

Variante 2 (execução paralela (mais rápida)):

someList.parallelStream().forEach(listItem -> {
    System.out.println(listItem);
});

Usando versões mais antigas do Java, incluindo o Java 7 você pode usar o loop foreach seguinte maneira.

List<String> items = new ArrayList<>();
        items.add("A");
        items.add("B");
        items.add("C");
        items.add("D");
        items.add("E");

        for(String item : items){
            System.out.println(item);
        }

A seguir, a maneira mais recente de usar o loop foreach no Java 8

(loop uma lista com a expressão forEach + lambda ou referência de método)

//lambda
    //Output : A,B,C,D,E
    items.forEach(item->System.out.println(item));


//method reference
    //Output : A,B,C,D,E
    items.forEach(System.out::println);

Para mais informações consulte este link.

https://www.mkyong.com/java8/java-8-foreach-examples/


for (Iterator<String> i = someIterable.iterator(); i.hasNext();) {
    String item = i.next();
    System.out.println(item);
}

Note que se você precisar usar i.remove(); Em seu loop, ou acessar o iterador real de alguma forma, você não pode usar o idioma for ( : ) :), uma vez que o iterador real é meramente inferido.

Como foi observado por Denis Bueno, esse código funciona para qualquer objeto que implemente a interface Iterable .

Além disso, se o lado direito do idioma for for (:) for uma array vez de um objeto Iterable , o código interno usará um contador de índice int e verificará array.length . Veja a especificação da linguagem Java .


public static Boolean Add_Tag(int totalsize)
{ List<String> fullst = new ArrayList<String>();
            for(int k=0;k<totalsize;k++)
            {
              fullst.addAll();
            }
}

List<Item> Items = obj.getItems();
for(Item item:Items)
             {
                System.out.println(item); 
             }

Itera sobre todos os objetos na tabela Itens.





syntactic-sugar