4.2.2 La sentencia for
Python permite recorrer aquellos tipos de datos que sean iterables, es decir, que admitan iterar sobre ellos. Algunos ejemplos de tipos y estructuras de datos que permiten ser iteradas (recorridas) son: cadenas de texto, listas, diccionarios, ficheros, etc. La sentencia for nos permite realizar esta acción.
A continuación se plantea un ejemplo en el que vamos a recorrer (iterar) una cadena de texto:
La clave aquí está en darse cuenta que el bucle va tomando, en cada iteración, cada uno de los elementos de la variable que especifiquemos. En este caso concreto letter va tomando cada una de las letras que existen en word, porque una cadena de texto está formada por elementos que son caracteres.
Ejecución paso a paso a través de Python Tutor:
Romper un bucle for
Una sentencia break dentro de un for rompe el bucle, igual que veíamos para los bucles while. Veamos un ejemplo con el código anterior. En este caso vamos a recorrer una cadena de texto y pararemos el bucle cuando encontremos una letra t minúscula:
Ejecución paso a paso a través de Python Tutor:
Truco: Tanto la comprobación de rotura de un bucle como la continuación a la siguiente iteración se llevan a cabo del mismo modo que hemos visto con los bucles de tipo while.
Ejercicio
Dada una cadena de texto, indique el número de vocales que tiene.
Ejemplo
- Entrada: Supercalifragilisticoespialidoso
- Salida: 15
Secuencias de números
Es muy habitual hacer uso de secuencias de números en bucles. Python no tiene una instrucción específica para ello. Lo que sí aporta es una función range() que devuelve un flujo de números en el rango especificado. Una de las grandes ventajas es que la «lista» generada no se construye explícitamente, sino que cada valor se genera bajo demanda. Esta técnica mejora el consumo de recursos, especialmente en términos de memoria.
La técnica para la generación de secuencias de números es muy similar a la utilizada en los «slices» de cadenas de texto. En este caso disponemos de la función range(start, stop, step):
- start: Es opcional y tiene valor por defecto 0.
- stop: es obligatorio (siempre se llega a 1 menos que este valor).
- step: es opcional y tiene valor por defecto 1.
range() devuelve un objeto iterable, así que iremos obteniendo los valores paso a paso con una sentencia for … in. Veamos diferentes ejemplos de uso:
Rango: [0,1,2]
Rango: [1, 3, 5]
Rango: [2, 1, 0]
Ejecución paso a paso a través de Python Tutor:
Truco: Se suelen utilizar nombres de variables i, j, k para lo que se denominan contadores. Este tipo de variables toman valores numéricos enteros como en los ejemplos anteriores. No conviene generalizar el uso de estas variables a situaciones en las que, claramente, tenemos la posibilidad de asignar un nombre semánticamente más significativo. Esto viene de tiempos antiguos en FORTRAN donde i era la primera letra que tenía valor entero por defecto.
Ejercicio
Determine si un número dado es un número primo.
No es necesario implementar ningún algoritmo en concreto. La idea es probar los números menores al dado e ir viendo si las divisiones tienen resto cero o no.
¿Podría optimizar su código? ¿Realmente es necesario probar con tantos divisores?
Ejercicio
- Entrada: 11
- Salida: Es primo
Usando el guión bajo
Nivel avanzado
Hay situaciones en las que no necesitamos usar la variable que toma valores en el rango, sino que únicamente queremos repetir una acción un número determinado de veces.
Para estos casos se suele recomendar usar el guión bajo _ como nombre de variable, que da a entender que no estamos usando esta variable de forma explícita:
Como ya vimos en las sentencias condicionales, el anidamiento es una técnica por la que incluimos distintos niveles de encapsulamiento de sentencias, unas dentro de otras, con mayor nivel de profundidad. En el caso de los bucles también es posible hacer anidamiento.
Veamos un ejemplo de 2 bucles anidados en el que generamos todas las tablas de multiplicar:
Lo que está ocurriendo en este código es que, para cada valor que toma la variable i, la otra variable j toma todos sus valores. Como resultado tenemos una combinación completa de los valores en el rango especificado.
Ejecución paso a paso a través de Python Tutor:
- Podemos añadir todos los niveles de anidamiento que queramos. Eso sí, hay que tener en cuenta que cada nuevo nivel de anidamiento supone un importante aumento de la complejidad ciclomática de nuestro código, lo que se traduce en mayores tiempos de ejecución.
- Los bucles anidados también se pueden aplicar en la sentencia while.
Ejercicio
Imprima los 100 primeros números de la sucesión de Fibonacci:
0,1,1,2, 3, 5,8,13, 21, 34, 55, 89,…
- Escriba un programa en Python que realice las siguientes 9 multiplicaciones. ¿Nota algo raro? (solución)
- Escriba un programa en Python que acepte una cadena de texto e indique si todos sus
- Entrada: hello-world
- Salida: Se han encontrado caracteres no alfabéticos
- Escriba un programa en Python que acepte un número entero ny realice el siguiente cálculo de productos sucesivos (solución):
- Escriba un programa en Python que acepte dos cadenas de texto y compute el produc
- Entrada: str1=abc; str2=123 • Salida: al a2 a3 b1 b2 b3 c1 c2 c3
- Escriba un programa en Python que acepte dos valores enteros (x e y) que representar
- Entrada: objetivo_x=7; objetivo_y=8;
- Salida: (0, 0) (1, 2) (3, 3) (4, 5) (6, 6) (7, 8)
- Escriba un programa que calcule la distancia hamming entre dos cadenas de texto de l
- Entrada: 0001010011101 y 0000110010001
- Salida: 4
AMPLIAR CONOCIMIENTOS
- The Python range() Function
- How to Write Pythonic Loops
- For Loops in Python (Definite Iteration)
- Python «while» Loops (Indefinite Iteration)