2010-11-18 6 views
7

Hi Sono principiante in java e il mio programma ha 4 cicli for: il mio programma funziona in questo modo che, se b è true, l'elemento verrà rimosso dalla pointList e n sarà n-- e ho voglia di uscire da tutte le per loops e vieni di nuovo dal primo ciclo for così l sarà l++, come posso fare questo? con dichiarazione di rottura?come possiamo uscire da 4 inner for loops?

for (int l = 0; l < n; l++) { 
    for (int i = 1; i < (n - 2); i++) { 
     for (int j = i + 1; j < (n - 1); j++) { 
      for (int k = j + 1; k < n; k++) { 
       if (l != i && l != j && l != k) { 
        boolean b = isOK(pointList.get(l), pointList.get(i), pointList.get(j), pointList.get(k)); 
        System.out.println(b); 
        if (b == true) { 
         pointList.remove(pointList.get(l); 
         n--; 
         break; 
        } 
        else 
         System.out.println(b); 
       } 
      } 
     } 
    } 
} 
+0

duplicato http: // stackoverflow.it/questions/551578/how-to-break-multiple-foreach-loop – SunnyShah

+0

Forse potresti descrivere in poche parole cosa vuoi fare? msgstr "rimuovere l-esimo elemento se b è vero". Il tuo codice contiene errori di sintassi. Risolvilo, per favore, e chiarisci la tua domanda. – khachik

+0

Sembra che tu stia cercando di trovare 4 elementi che soddisfano alcuni criteri. Se hai spiegato quali erano i criteri, forse potremmo suggerire un modo più semplice di fare la stessa cosa. per esempio. forse ordinare prima l'elenco potrebbe semplificare i loop. –

risposta

17

Si può fare uso di una rottura etichettato come:

 for (int l = 0; l < n; l++) { 
foo: for (int i = 1; i < (n - 2); i++) { 
      for (int j = i + 1; j < (n - 1); j++) { 
       for (int k = j + 1; k < n; k++) { 
        if (l != i && l != j && l != k) { 
         boolean b = isOK(pointList.get(l), pointList.get(i), pointList.get(j), pointList.get(k)); 
         System.out.println(b); 
         if (b == true) { 
          pointList.remove(pointList.get(l); 
          n--; 
          break foo; 
         } 
         else 
          System.out.println(b); 
        } 

       } 

      } 
     } 
    } 
+0

questo è un goto travestito, giusto? :) – lorenzog

+0

interromperà solo gli ultimi tre cicli, quindi inizierà con il primo ciclo e si sposterà anche all'interno di questi tre cicli? – user472221

+1

Suppongo che qualsiasi affermazione di ramificazione sia un "goto travestito". Ma hanno tutti i loro limiti e i loro usi. Anche goto stesso, in realtà (le macchine di stato sono una PITA senza di essa). –

3
String valueFromObj2 = null; 
String valueFromObj4 = null; 
OUTERMOST: for(Object1 object1: objects){ 
    for(Object2 object2: object1){ 
    //I get some value from object2 
    valueFromObj2 = object2.getSomeValue(); 
    for(Object3 object3 : object2){ 
     for(Object4 object4: object3){ 
     //Finally I get some value from Object4. 
     valueFromObj4 = object4.getSomeValue(); 
     //Compare with valueFromObj2 to decide either to break all the foreach loop 
     if(compareTwoVariable(valueFromObj2, valueFromObj4)) { 
      break OUTERMOST; 
     } 
     }//fourth loop ends here 
    }//third loop ends here 
    }//second loop ends here 
}//first loop ends here 
+0

preso da http://stackoverflow.com/questions/551578/how-to-break-multiple-foreach-loop – SunnyShah

0

Una prima soluzione 'rapida e sporca' sarebbe quella di utilizzare una variabile stay_into_loops e modificare il for cicli piace:

boolean stay_into_loops = true 
// here goes the first for loop 
for (int i = 1; i < (n - 2) && stay_into_loops ; i++) { 
      for (int j = i + 1; j < (n - 1) && stay_into_loops ; j++) { 
       for (int k = j + 1; k < n && stay_into_loops ; k++) { 
        if (l != i && l != j && l != k) { 
         boolean b = isOK(pointList.get(l), `pointList.get(i), pointList.get(j), pointList.get(k));` 
         System.out.println(b); 
         if (b == true) { 
          pointList.remove(pointList.get(l); 
          n--; 
          stay_into_loops = false; 
          break; 

Tuttavia è in genere un odore di codice quando si incontrano le cose come queste. Prendi in considerazione il refactoring del codice perché a un certo punto questo si trasformerà in un disastro.

5

In un ciclo l'istruzione break termina il ciclo interno mentre continue passa all'iterazione successiva. Affinché queste due istruzioni funzionino su un loop diverso da quello interno, è necessario utilizzare labels. Qualcosa del genere dovrebbe funzionare:

outerloop:  
     for (int l = 0; l < n; l++) { 
      for (int i = 1; i < (n - 2); i++) { 
       for (int j = i + 1; j < (n - 1); j++) { 
        for (int k = j + 1; k < n; k++) { 
         if (l != i && l != j && l != k) { 
          boolean b = isOK(pointList.get(l), pointList.get(i), pointList.get(j), pointList.get(k)); 
          System.out.println(b); 
          if (b == true) { 
           pointList.remove(pointList.get(l); 
           n--; 
           continue outerloop; 
          } 
          else 
           System.out.println(b); 
         } 

        } 

       } 
      } 
     } 
+0

perfetto come si arriva. grazie –

2

utilizzare un ciclo etichettato

for (int l = 0; l < n; l++) { 
    loopa: 
    for (int i = 1; i < (n - 2); i++) { 
     for (int j = i + 1; j < (n - 1); j++) { 
      for (int k = j + 1; k < n; k++) { 
       if (l != i && l != j && l != k) { 
        boolean b = isOK(pointList.get(l), pointList.get(i), pointList.get(j), pointList.get(k)); 
        System.out.println(b); 
        if (b == true) { 
         pointList.remove(pointList.get(l); 
         n--; 
         break loopa; 
        } 
        else 
         System.out.println(b); 
       } 

      } 

     } 
    } 
} 

e poi pausa dal ciclo etichettato

+0

interromperà solo gli ultimi tre cicli, quindi inizierà con il primo ciclo e anche all'interno di questi tre cicli? – user472221

+0

Funzionalmente equivalente a quello del cervello. In questo modo si kick nella prossima iterazione del ciclo più esterno – stjohnroe

0

Crea un uscita per se stessi in ogni ciclo for interno.
Ecco una soluzione rapida e indolore.

bool breakout; 
    for (int l = 0; l < n; l++) 
    { 
     breakout = false; 
     for (int i = 1; i < (n - 2) && !breakout; i++) 
      for (int j = i + 1; j < (n - 1) && !breakout; j++) 
       for (int k = j + 1; k < n && !breakout; k++) 
       { 
        if(b == true) 
         breakout = true;        
       } 
    } 

in modo da vedere il booleano breakout è il vostro biglietto da ogni ciclo interno, coz viene controllato in ogni dichiarazione for. E si resetta ogni volta che il primo for itera.

1
again: 
for (int l = 0; l < n; l++) { 
     for (int i = 1; i < (n - 2); i++) { 
      for (int j = i + 1; j < (n - 1); j++) { 
       for (int k = j + 1; k < n; k++) { 
        if (l != i && l != j && l != k) { 
         boolean b = isOK(pointList.get(l), pointList.get(i), pointList.get(j), pointList.get(k)); 
         System.out.println(b); 
         if (b == true) { 
          pointList.remove(pointList.get(l); 
          n--; 
          break again; 
         } 
         else 
          System.out.println(b); 
        } 

       } 

      } 
     } 
    } 
+0

Penso che voglia CONTINUARE il ciclo 'for (int l ...' e non uscirne ... –

1

Sono d'accordo con tutte le altre risposte. Tuttavia, vorrei sottolineare che un'alternativa a exit sarebbe quella di inserire il codice nella propria routine e utilizzare un'istruzione return per uscire dall'intera cosa. Il tuo ciclo quad-nest è così complesso di per sé che probabilmente merita comunque di essere nella sua routine.

Ho lavorato a lavori DoD che richiedevano uno cyclomatic complexity di non più di 6 per una qualsiasi routine (con alcune eccezioni). Questa serie di loop da sola è 4. Se non riesci a trovare un modo più semplice per farlo, dovresti proprio metterli nella loro routine solo per preservare la sanità mentale dei poveri schmuck che devono mantenere questo codice.