Ejercicios listas

# =============================================================================
# RECORRER LISTAS EN PYTHON — PATRONES HABITUALES
# =============================================================================
# En este programa veremos tres patrones muy comunes cuando trabajamos con listas:
#
#   1. Buscar el elemento "mejor" de una lista (el más largo, el mayor, el menor...)
#   2. Filtrar una lista: quedarse solo con los elementos que cumplan una condición
#   3. Filtrar con condiciones sobre cadenas (primera letra, última letra...)
#
# Estos tres patrones aparecen constantemente en programas reales.
# =============================================================================


# =============================================================================
# PATRÓN 1: BUSCAR EL NOMBRE MÁS LARGO DE UNA LISTA
# =============================================================================
# Problema: dada una lista de nombres, ¿cuál es el más largo?
#
# Estrategia: "candidato provisional"
#   Asumimos que el primero es el más largo.
#   Recorremos el resto y si encontramos uno más largo, lo sustituimos.
#   Al terminar, el candidato es el ganador real.
# =============================================================================

alumnos = ["Ana", "Rosa", "Pep", "Iu", "Felicia", "Juan"]
# Lista de nombres con la que vamos a trabajar.
# ALTERNATIVA: pedir los nombres al usuario con un bucle while.

nombre_mas_largo = alumnos[0]
# Tomamos el PRIMER elemento como candidato provisional al más largo.
# alumnos[0] → "Ana"
# No lo inicializamos a "" porque "" tiene longitud 0 y cualquier nombre
# sería más largo, lo que también funcionaría, pero esta forma es más clara.
# IMPORTANTE: hacerlo ANTES del bucle, no dentro.

for alumno in alumnos:
    # Recorremos TODOS los alumnos, incluido "Ana" (el primero).
    # Comparar "Ana" consigo mismo no causa ningún problema: len("Ana") > len("Ana")
    # es False, así que simplemente no lo sustituimos. Todo correcto.

    if len(alumno) > len(nombre_mas_largo):
        # len() devuelve el número de caracteres de una cadena.
        # len("Ana")     → 3
        # len("Felicia")  → 7
        # Si el alumno actual tiene MÁS letras que el candidato actual...

        nombre_mas_largo = alumno
        # ...actualizamos el candidato. Ahora este es el más largo provisional.
        # Vuelta a vuelta:
        #   "Ana"     → candidato="Ana"     (inicial)
        #   "Rosa"    → 4 > 3 → candidato="Rosa"
        #   "Pep"     → 3 > 4 → NO cambia
        #   "Iu"      → 2 > 4 → NO cambia
        #   "Felicia" → 7 > 4 → candidato="Felicia"
        #   "Juan"    → 4 > 7 → NO cambia

print(nombre_mas_largo)
# → "Felicia"
#
# RETO: modifica el código para encontrar también el nombre MÁS CORTO.
# Pista: solo tienes que cambiar > por < y el nombre de la variable.


# =============================================================================
# PATRÓN 2: FILTRAR NÚMEROS DE UNA LISTA
# =============================================================================

notas = [3, 6, 7, 8, 2, 4, 9, 10]
# Lista de notas con la que trabajaremos.
# Queremos saber cuántos alumnos han aprobado y cuántos han suspendido.


# -----------------------------------------------------------------------------
# FUNCIÓN lista_mayores_que(lista, umbral)
# -----------------------------------------------------------------------------
# Recibe una lista de números y un umbral.
# Devuelve una nueva lista con solo los números ESTRICTAMENTE mayores que el umbral.
# La lista original no se modifica.
#
# Ejemplos:
#   lista_mayores_que([1, 5, 3, 8, 2, 9], 4)  →  [5, 8, 9]
#   lista_mayores_que([7, 7, 7], 7)            →  []  (7 no es mayor QUE 7)

def lista_mayores_que(lista, umbral):
    # Dos parámetros:
    #   "lista"   → la lista de números que queremos filtrar
    #   "umbral"  → el valor límite. Solo pasarán los números que lo superen.

    resultado = []
    # Lista vacía donde iremos guardando los números que cumplan la condición.
    # Debe crearse DENTRO de la función para que empiece vacía en cada llamada.
    # Si estuviera fuera, las llamadas anteriores dejarían números sobrantes.

    for numero in lista:
        # Recorremos cada número de la lista que nos han pasado.

        if numero > umbral:
            # Comprobamos si supera el umbral.
            # OJO: es > (estrictamente mayor), no >= (mayor o igual).
            # Por eso lista_mayores_que([7,7,7], 7) devuelve [] y no [7,7,7].
            # Si quisiéramos incluir el umbral cambiaríamos > por >=.

            resultado.append(numero)
            # .append() añade el número AL FINAL de la lista resultado.
            # Solo llegamos aquí si el número supera el umbral.

    return resultado
    # Devolvemos la lista con los números seleccionados.
    # Si ningún número superó el umbral, devolvemos [] (lista vacía).

# --- Casos de prueba ---
mayores = lista_mayores_que([1, 5, 3, 8, 2, 9], 4)
print(mayores)
# → [5, 8, 9]
# Guardamos el resultado en "mayores" para poder usarlo después si queremos.

print(lista_mayores_que([2, 10, 7, 40, 8, 3], 7))   # → [10, 40, 8]
print(lista_mayores_que([10, 20, 30], 15))            # → [20, 30]
print(lista_mayores_que([1, 2, 3], 10))               # → []
print(lista_mayores_que([7, 7, 7], 7))                # → []

# --- Uso práctico con las notas ---
# Aprobados: notas mayores que 4 (es decir, 5 o más)
# Suspensos: notas menores o iguales a 4
aprobados = lista_mayores_que(notas, 4)
# → [6, 7, 8, 9, 10]
# len(aprobados) nos diría cuántos hay: len([6,7,8,9,10]) = 5


# =============================================================================
# PATRÓN 3: FILTRAR NOMBRES SEGÚN SUS LETRAS
# =============================================================================
# Ahora filtramos una lista de cadenas comprobando la primera y última letra.
# Veremos dos herramientas nuevas:
#   nombre[0]   → primera letra  ("Ana"[0]  → "A")
#   nombre[-1]  → última letra   ("Ana"[-1] → "a")
#   .lower()    → convierte a minúscula para ignorar mayúsculas/minúsculas


# -----------------------------------------------------------------------------
# FUNCIÓN nombres_con_a(nombres)
# -----------------------------------------------------------------------------
# Recibe una lista de nombres.
# Devuelve una nueva lista con los nombres que empiecen O acaben por 'a' (o 'A').
#
# Ejemplos:
#   nombres_con_a(["Ana", "Pedro", "María", "Jordi", "Almudena"])
#       → ["Ana", "María", "Almudena"]

def nombres_con_a(nombres):

    resultado = []
    # Lista vacía donde iremos guardando los nombres que cumplan la condición.

    for nombre in nombres:
        # Recorremos cada nombre de la lista.

        letra_inicial = nombre[0].lower()
        # nombre[0]  → primera letra del nombre. "Ana"[0] → "A"
        # .lower()   → la convertimos a minúscula. "A".lower() → "a"
        # Así "Ana", "ANA" y "ana" funcionan igual: siempre comparamos con "a".
        # Sin .lower(), "Ana" empezaría por "A" y no pasaría el if letra=="a".

        letra_final = nombre[-1].lower()
        # nombre[-1] → última letra del nombre.
        # Los índices negativos en Python cuentan desde el final:
        #   nombre[-1] → última letra
        #   nombre[-2] → penúltima letra
        # "María"[-1] → "a"   "Pedro"[-1] → "o"
        # .lower() por el mismo motivo que antes.

        if letra_inicial == "a" or letra_final == "a":
            # "or" → basta con que UNA de las dos condiciones sea True.
            # Si el nombre empieza por 'a' → entra.
            # Si el nombre acaba por 'a'   → entra.
            # Si cumple las DOS           → también entra, pero solo se añade UNA vez.
            # Si no cumple ninguna        → no entra.
            #
            # Repaso con cada nombre de la prueba:
            #   "Ana"      → inicial="a" ✓ → entra
            #   "Pedro"    → inicial="p", final="o" → NO entra
            #   "María"    → inicial="m", final="a" ✓ → entra
            #   "Jordi"    → inicial="j", final="i" → NO entra
            #   "Almudena" → inicial="a" ✓, final="a" ✓ → entra (una sola vez)

            resultado.append(nombre)
            # Añadimos el nombre original (con sus mayúsculas/minúsculas originales)
            # no la versión .lower(). Queremos devolver "Ana", no "ana".

    return resultado
    # Devolvemos la lista con los nombres seleccionados.

# --- Casos de prueba ---
con_a = nombres_con_a(["Ana", "Pedro", "María", "Jordi", "Almudena"])
print(con_a)
# → ["Ana", "María", "Almudena"]

Publicado por

Juan Pablo Fuentes

Formador de programación y bases de datos