Introducci贸n
Contenido
Las declaraciones condicionales y los bucles son una herramienta muy importante en la programaci贸n. No hay muchas cosas que podamos hacer con c贸digo que solo se pueda ejecutar l铆nea por l铆nea.
Eso es lo que significa “control de flujo”: guiar la ejecuci贸n de nuestro programa, en lugar de dejar que se ejecute l铆nea por l铆nea independientemente de cualquier factor interno o externo. Cada lenguaje de programaci贸n admite alguna forma de control de flujo, si no expl铆citamente a trav茅s de if
sy for
s o declaraciones similares, entonces impl铆citamente nos da las herramientas para crear tales construcciones, es decir, los lenguajes de programaci贸n de bajo nivel generalmente logran ese efecto con una gran cantidad de go-to
comandos.
Los bucles eran un concepto que se usaba mucho antes de que la programaci贸n de computadoras existiera, pero la primera persona en usar un bucle de software fue Ada Lovelace, com煤nmente conocida por su apellido de soltera, Byron, mientras calculaba N煤meros de Bernoulli, all谩 por el siglo XIX.
En Java, hay varias formas de controlar el flujo del c贸digo:
- declaraciones if y if-else
- cambiar declaraciones
- declaraciones while y do-while
- bucles for y for-each
break
ycontinue
declaraciones
romper
los break
declaraci贸n es una de las “declaraciones de salto” de Java, ya que transfiere la ejecuci贸n del c贸digo a otra parte del c贸digo. Ya hemos visto el break
palabra clave utilizada en la declaraci贸n de cambio. Lo revisaremos aqu铆, junto con otros casos de uso:
- Se puede utilizar para detener la ejecuci贸n de un
switch
caso de declaraci贸n, en lugar de dejar que contin煤e ejecutando c贸digo para los siguientes casos tambi茅n - Se puede usar para salir de un bucle antes de que haya terminado todas sus iteraciones, o como una forma de salir de bucles infinitos creados a prop贸sito.
- Se puede utilizar como una forma aceptable de la declaraci贸n “ir a” cuando tenemos varios bucles anidados.
Los dos primeros son relativamente similares, ya que ambos se utilizan para finalizar prematuramente la ejecuci贸n de uno o m谩s bloques de c贸digo:
// Finding at which index element a is in an array
int[] arr = {1,2,3,4,5,6};
int foundAt = -1;
int a = 4;
for (int i = 0; i < arr.length; i++) {
System.out.println(arr[i]);
if (arr[i] == a) {
foundAt = i;
break;
}
}
if (foundAt != -1)
System.out.println(a + " was found at index " + foundAt);
else System.out.println(a + " wasn't found in the array");
Salida:
1
2
3
4
4 was found at index 3
Como podemos ver, el for
bucle ejecutado como de costumbre hasta que se encontr贸 con el break
declaraci贸n, en cuyo punto Java dej贸 de ejecutar el ciclo y continu贸 la ejecuci贸n en la primera l铆nea despu茅s de la for
lazo.
Aqu铆 hay otro ejemplo:
Scanner s = new Scanner(System.in);
while (true) {
System.out.println("Do you wish to exit the infinite loop? Y/N");
if (s.hasNext()) {
String answer = s.next();
if (answer.equals("Y") || answer.equals("y"))
break;
}
}
Este bucle seguir谩 preguntando al usuario si desea salir del bucle hasta que responda con los caracteres apropiados, donde salimos del bucle usando break
, o terminar el programa con Ctrl + C
.
Por defecto el break
declaraci贸n solo sale del bucle m谩s interno en el que se encuentra.
Si quisi茅ramos encontrar la primera posici贸n en la que se puede encontrar cierto elemento en una matriz, y quisi茅ramos break
fuera de los bucles tan pronto como lo encontramos (similar al ejemplo con una matriz anterior), escribir lo siguiente no funcionar铆a:
int[][] matrix = {{1,2,3},{4,5,6},{7,8,9}};
int foundAtI = -1;
int foundAtJ = -1;
int a = 4;
for (int i = 0; i < matrix.length; i++) {
for (int j = 0; j < matrix[i].length; j++) {
System.out.print(matrix[i][j] + " ");
if (matrix[i][j] == a) {
foundAtI = i;
foundAtJ = j;
break;
}
}
System.out.println();
}
System.out.println();
if (foundAtI != -1)
System.out.println(a + " was found at indices [" + foundAtI + "," + foundAtJ + "]");
else System.out.println(a + " wasn't found in the matrix");
Salida:
1 2 3
4
7 8 9
4 was found at indices [1,0]
Podemos ver que el bucle continu贸 ejecut谩ndose incluso despu茅s de encontrar 4 en la matriz, despu茅s de tartamudear en la fila en la que se encontraba 4. Esto es porque el break
solo sali贸 del bucle m谩s interno, es decir, dej贸 de recorrer la fila actual y pas贸 a la siguiente. Adem谩s, nuestra tarea era encontrar la primera aparici贸n de 4 en la matriz, y de esta forma devolver铆amos la 煤ltima aparici贸n de 4 en nuestra matriz.
Aqu铆 es donde entran en juego las declaraciones etiquetadas, que veremos a continuaci贸n.
Declaraciones etiquetadas
Las declaraciones etiquetadas se pueden utilizar junto con break
o continue
declaraciones para simular una go-to
.
Las etiquetas se pueden aplicar a cualquier bloque de c贸digo entre {}
, for
, for-each
, while
, do-while
, if
y switch
declaraciones, as铆 como expresiones, asignaciones, return
declaraciones, try
bloques, y throw
declaraciones. Luego los usamos con el break
y continue
declaraciones.
Las etiquetas funcionan aplicando un identificador a una construcci贸n:
Identifier : Construct
Como:
someLoop: for (int i = 0; i < 100; i++) {}
someLabel: {
int i = 10;
}
Luego podemos recurrir a estas declaraciones etiquetadas a trav茅s de un break
o continue
. Por ejemplo, aqu铆 hemos etiquetado nuestro bucle externo como simplemente outer
. Para salir de dos o m谩s bucles anidados, break
el bucle exterior llamando a la etiqueta:
outer: for (int i = 0; i < matrix.length; i++) {
for (int j = 0; j < matrix[i].length; j++) {
System.out.print(matrix[i][j] + " ");
if (matrix[i][j] == a) {
foundAtI = i;
foundAtJ = j;
break outer;
}
}
System.out.println();
}
El uso de este ciclo etiquetado en lugar del ciclo en el ejemplo anterior produce el resultado y el comportamiento correctos:
1 2 3
4
4 was found at indices [1,0]
No puedes usar break label
Si el break
no se encuentra dentro de un bloque de c贸digo designado por esa etiqueta o provocar谩 un error durante la compilaci贸n.
Seguir
los continue
declaraci贸n simplemente omite el resto de la iteraci贸n actual y pasa a la siguiente. Es 煤til cuando queremos omitir iteraciones completas (o parte de) que cumplen ciertas condiciones, especialmente si tienen un alto rendimiento.
Para while
bucle, “omitir” el resto de la iteraci贸n significa volver directamente a verificar la condici贸n antes de la siguiente iteraci贸n, y para un for
bucle esto significa ir a la parte “paso” del for
loop (la parte donde normalmente incrementamos / decrementamos la variable de control) y luego verificamos la condici贸n antes de la siguiente iteraci贸n.
continue
se usa generalmente con un if
declaraci贸n -> lo haremos continue
si se cumple una determinada condici贸n. Usamos esto if
para ejecutar el resto de la iteraci贸n solo si no se cumple la condici贸n y omitir el uso continue
. Por ejemplo
// We want to print every number from 1 to 20, except those divisible by 3
for (int i = 1; i <= 20; i++) {
if (i % 3 == 0)
continue;
System.out.println(i);
}
los continue
en nuestro ejemplo podr铆a evitarse f谩cilmente utilizando un if
declaraci贸n, principalmente imprimiendo el n煤mero si i % 3 != 0
es cierto, de lo contrario no hace nada.
Consejos generales sobre ambos break
y especialmente) continue
es intentar usarlos principalmente al comienzo de las iteraciones como alguna forma de condiciones previas que estamos verificando. Usando un continue
en alg煤n lugar en el medio de la iteraci贸n es una excelente manera de causar errores que te llevar谩n un tiempo resolver.
Por supuesto, tambi茅n puedes usar continue
con declaraciones etiquetadas:
start: for (int i = 0; i < 10; i++) {
System.out.println();
for (int j = 0; j < 10; j++) {
if (j >= i)
continue start;
}
System.out.println("Since j will always be equal to or more than i, the 'start' loop will continue running indefinitely, and this piece of code will never run.");
}
Conclusi贸n
El control de flujo en el c贸digo es esencial en casi todas las aplicaciones. Las declaraciones que alteran el flujo del c贸digo son bloques de construcci贸n fundamentales y cada desarrollador aspirante debe tener el control total / ser consciente de c贸mo funcionan.
Utilizando el break
y continue
declaraciones, los desarrolladores de Java pueden simular go-to
declaraciones y romper ciertos bucles si es necesario.