← CC2005

Strings

Semestre 02, 2026

El texto como dato

  • Buena parte de los datos que procesa un programa es texto.
  • Nombres, correos, direcciones, respuestas del usuario y nombres de archivo son texto.
  • Ese texto casi nunca llega limpio ni en el formato que se necesita.

Texto sin herramientas

Se requiere saber si el correo que escribió el usuario tiene el símbolo arroba.


correo = input("Correo: ")

# ¿y ahora qué?
Lo importante

Con lo visto hasta ahora el texto solo se puede guardar e imprimir. Hace falta una forma de medirlo, recorrerlo, buscar dentro de él y transformarlo.

Strings

Definición

Un string es una secuencia ordenada de caracteres. Cada carácter ocupa una posición numerada que se llama índice.


nombre = "María"
mensaje = 'Hola, mundo'

Una secuencia, no un bloque

La palabra Python guardada en una variable se ve así por dentro.

CarácterPython
Índice012345
Consecuencia

Al ser una secuencia, un string se puede medir, indexar, cortar y recorrer con un ciclo, igual que cualquier otra colección ordenada.

Operaciones sobre un string

Obtener su longitud
Acceder a caracteres individuales
Extraer partes del texto
Recorrerlo con un ciclo
Transformarlo con métodos
Buscar contenido dentro de él

Comillas simples y dobles

Python acepta ambas y el resultado es idéntico.


a = "Hola"
b = 'Hola'
Regla

La comilla que abre el string es la que lo cierra. Mezclarlas produce un error de sintaxis.

Comillas dentro del texto

Tener dos tipos de comillas resuelve el caso en que el texto incluye una de ellas.


frase = 'Ella dijo "hola" y se fue'
otra = "No se puede, está ocupado"
Criterio

Si el texto lleva comillas dobles se usan simples por fuera, y al revés.

Secuencias de escape

Algunos caracteres no se pueden escribir directamente y se representan con una barra invertida.

SecuenciaSignificado
\nSalto de línea
\tTabulación
\"Comilla doble literal
\'Comilla simple literal
\\Barra invertida literal

Escape en la práctica


print("Línea 1\nLínea 2")
print("Nombre:\tAna")
print("Dijo \"hola\"")

Línea 1
Línea 2
Nombre:	Ana
Dijo "hola"
Nótese

La barra invertida y la letra son dos caracteres en el código, pero uno solo dentro del string. Por eso len de barra n es 1.

Strings de varias líneas

Tres comillas permiten escribir un texto largo conservando los saltos de línea.


menu = """1. Agregar
2. Consultar
3. Salir"""

print(menu)

Longitud de un string

Definición

La función len devuelve el número de caracteres de un string.


texto = "Python"
print(len(texto))    # 6

Todo carácter cuenta


print(len("Hola mundo"))   # 10, el espacio cuenta
print(len("¡Hola!"))       # 6, los signos cuentan
print(len(""))             # 0, string vacío
Detalle

Espacios, signos de puntuación y acentos son caracteres como cualquier otro. El string vacío existe y su longitud es cero.

Validar una longitud mínima

Se requiere rechazar contraseñas de menos de ocho caracteres.


contrasena = input("Escribe tu contraseña: ")

if len(contrasena) < 8:
    print("La contraseña es demasiado corta.")
else:
    print("Contraseña aceptada.")

Índices

Definición

Cada carácter de un string tiene una posición llamada índice. La numeración empieza en cero.

CarácterPython
Índice012345
Desde el final-6-5-4-3-2-1

Acceder a un carácter

El índice se escribe entre corchetes después del string.


texto = "Python"

print(texto[0])   # P
print(texto[1])   # y
print(texto[5])   # n

Índices negativos

Los índices negativos cuentan desde el final hacia atrás.


texto = "Python"

print(texto[-1])  # n
print(texto[-2])  # o
print(texto[-6])  # P
Utilidad

Permiten tomar el último carácter sin conocer la longitud del string.

Índice fuera de rango


texto = "Python"
print(texto[6])   # IndexError
Regla

El índice máximo es len del texto menos uno. Un string de seis caracteres llega hasta el índice cinco.

Slicing

Definición

Un slice extrae una porción del string. Se escribe con el índice inicial y el final separados por dos puntos.


texto[inicio:fin]

El carácter en la posición final no se incluye.

El final no se incluye

ExpresiónResultadoCaracteres tomados
texto[0:3]Pytíndices 0, 1 y 2
texto[2:5]thoíndices 2, 3 y 4
texto[1:4]ythíndices 1, 2 y 3
Atajo mental

La cantidad de caracteres que devuelve un slice es el final menos el inicio.

Omitir el inicio o el final


texto = "Python"

print(texto[:3])    # Pyt, desde el inicio
print(texto[3:])    # hon, hasta el final
print(texto[:])     # Python, copia completa
Comodidad

Omitir un extremo evita tener que calcular la longitud del string.

Slice con paso

Un tercer valor indica cada cuántos caracteres se avanza.


texto = "Python"

print(texto[::2])    # Pto, de dos en dos
print(texto[::-1])   # nohtyP, al revés
Nótese

Un paso negativo recorre el string de derecha a izquierda, así que invertir un texto cabe en una sola expresión.

Separar un correo con slices

Se requiere obtener el usuario y el dominio de un correo conocido.


correo = "[email protected]"

print(correo[:7])    # usuario
print(correo[8:])    # uvg.edu.gt
Limitación

Las posiciones están escritas a mano, por lo que el programa solo funciona con ese correo. Más adelante los métodos resuelven el caso general.

Recorrer un string

Al ser una secuencia, un string se puede recorrer con for sin necesidad de índices.


nombre = "Ana"

for letra in nombre:
    print(letra)
Resultado

Se imprimen A, n y a, cada una en su propia línea. La variable del ciclo recibe un carácter por vuelta.

Recorrer con el índice

Cuando se necesita la posición además del carácter, se recorre el rango de la longitud.


texto = "Python"

for i in range(len(texto)):
    print(i, texto[i])
Criterio

Si la posición no hace falta, se prefiere la primera forma porque es más corta y no puede salirse del rango.

El operador in

El operador in responde si un texto aparece dentro de otro.


frase = "El cielo es azul"

print("azul" in frase)        # True
print("verde" in frase)       # False
print("verde" not in frase)   # True
Alcance

Funciona igual con un carácter y con una palabra completa, y devuelve un valor booleano que se puede usar directamente en un if.

Contar vocales en una palabra

Se requiere contar cuántas vocales tiene un texto, recorriéndolo carácter por carácter.


texto = "murciélago"
vocales = "aeiouáéíóú"
contador = 0

for letra in texto:
    if letra in vocales:
        contador = contador + 1

print("Vocales:", contador)   # 5

Inmutabilidad

Definición

Un string no se puede modificar después de creado. Ninguna operación cambia el string original.


texto = "Python"
texto[0] = "p"   # TypeError

Construir un string nuevo

La solución no es modificar, sino armar otro string a partir del original.


texto = "Python"
nuevo = "p" + texto[1:]

print(nuevo)   # python
Patrón

Se toma la parte que se conserva con un slice y se concatena con la parte nueva.

Los métodos devuelven un valor


nombre = "Carlos"
nombre.upper()

print(nombre)   # Carlos, sin cambio
Consecuencia

El método se ejecutó y produjo un string nuevo, pero nadie lo guardó, así que el resultado se perdió.

Guardar el resultado


nombre = "Carlos"
resultado = nombre.upper()

print(resultado)   # CARLOS
print(nombre)      # Carlos
Regla

Todo método de string devuelve un valor que hay que asignar a una variable o usar de inmediato.

Concatenación

El operador más une dos strings en uno nuevo.


saludo = "Hola"
nombre = "Luis"

mensaje = saludo + ", " + nombre + "!"
print(mensaje)   # Hola, Luis!

Concatenar tipos distintos


edad = 22
print("Tengo " + edad + " años")    # TypeError
print("Tengo " + str(edad) + " años")
Regla

El operador más solo une strings con strings. Un número se convierte antes con la función str.

Acumular texto en un ciclo

Se requiere armar una sola línea con los números del uno al cinco.


resultado = ""

for i in range(1, 6):
    resultado = resultado + str(i) + " "

print(resultado)   # 1 2 3 4 5
Patrón acumulador

La variable empieza vacía y en cada vuelta se reasigna con su contenido anterior más la parte nueva.

Repetición

El operador por repite un string la cantidad de veces indicada.


linea = "-" * 20
separador = "=-" * 10

print(linea)
print(separador)
Uso típico

Sirve para dibujar separadores y bordes en la salida sin escribir veinte guiones a mano.

Comparar strings

Los operadores de igualdad funcionan con strings y comparan carácter por carácter.


print("hola" == "hola")   # True
print("hola" == "Hola")   # False
print("hola" != "Hola")   # True
Cuidado

La comparación distingue mayúsculas de minúsculas, así que hola y Hola son dos strings diferentes.

Comparar sin importar el formato

Se requiere aceptar la respuesta del usuario escrita de cualquier forma.


respuesta = input("¿Continuar? (si/no): ")

if respuesta.strip().lower() == "si":
    print("Continuando...")
Técnica

Normalizar la entrada antes de compararla acepta SI, Si y si con espacios sobrantes, sin escribir un if por cada variante.

Métodos de strings

Definición

Un método es una función que pertenece a un tipo de dato. Se llama escribiendo un punto después del string.


texto.metodo()

Cuatro familias de métodos

Transformar: cambian el formato del texto
Buscar: ubican o cuentan contenido
Dividir y unir: convierten entre texto y partes
Validar: responden qué contiene el texto
Constante

Ninguno modifica el string original. Todos devuelven un valor nuevo.

Mayúsculas y minúsculas


texto = "hola Mundo"

print(texto.upper())        # HOLA MUNDO
print(texto.lower())        # hola mundo
print(texto.capitalize())   # Hola mundo
print(texto.title())        # Hola Mundo
Diferencia

capitalize pone en mayúscula solo la primera letra del texto, mientras title lo hace con la primera letra de cada palabra.

Eliminar espacios con strip


entrada = "   Python   "

print(entrada.strip())    # "Python"
print(entrada.lstrip())   # "Python   "
print(entrada.rstrip())   # "   Python"
Uso típico

Se aplica a toda entrada del usuario, porque un espacio invisible al final arruina cualquier comparación.

Reemplazar con replace


frase = "Me gusta el café con café"

print(frase.replace("café", "té"))
# Me gusta el té con té

print(frase.replace("café", "té", 1))
# Me gusta el té con café
Detalle

Por defecto reemplaza todas las apariciones. Un tercer argumento limita cuántas se cambian.

Buscar con find


texto = "El gato está en el tejado"

print(texto.find("gato"))    # 3
print(texto.find("perro"))   # -1
Valor de retorno

Devuelve el índice donde empieza la primera aparición, o menos uno cuando el texto no está. Nótese que menos uno no significa la última posición.

find frente a in

in responde si el texto está o no
find responde en qué posición está
Criterio

Si la posición no se va a usar, in deja el código más claro que comparar el resultado de find contra menos uno.

Contar con count


frase = "ana banana"

print(frase.count("a"))     # 6
print(frase.count("ana"))   # 2
print(frase.count("z"))     # 0
Detalle

Las apariciones no se traslapan. En banana hay dos veces ana solo si se cuenta la primera y luego se sigue desde donde terminó.

Verificar inicio y final


archivo = "informe_final.pdf"

if archivo.endswith(".pdf"):
    print("Es un PDF")

if archivo.startswith("informe"):
    print("Es un informe")
Uso típico

Reconocer extensiones de archivo, prefijos de código y dominios de correo sin calcular índices.

Dividir con split

split separa un string en varias partes y las entrega en una lista.


frase = "manzana naranja uva"

frutas = frase.split()
print(frutas)      # ['manzana', 'naranja', 'uva']
print(frutas[0])   # manzana
Adelanto

La lista es el tema de la siguiente clase. Por ahora basta saber que guarda varios valores y que cada uno se obtiene con un índice.

split con separador

Sin argumentos separa por espacios. Con un argumento separa por el texto indicado.


fecha = "2026-04-15"
partes = fecha.split("-")

print(partes[0])   # 2026
print(partes[1])   # 04
print(partes[2])   # 15

Leer un registro separado por comas

Se requiere separar los campos de una línea que viene de un archivo.


linea = "Pedro,25,Guatemala"
datos = linea.split(",")

print(f"Nombre: {datos[0]}")
print(f"Edad: {datos[1]}")
print(f"País: {datos[2]}")

Unir con join

join hace lo contrario de split, pues toma varias partes y las vuelve un solo string.


palabras = ["Hola", "desde", "Python"]

print(" ".join(palabras))    # Hola desde Python
print("-".join(palabras))    # Hola-desde-Python
Nótese

El separador es el string sobre el que se llama al método, y las partes van como argumento.

Verificar el contenido


print("12345".isdigit())    # True, solo dígitos
print("Hola".isalpha())     # True, solo letras
print("abc123".isalnum())   # True, letras y dígitos
print("   ".isspace())      # True, solo espacios
Detalle

Todos devuelven un booleano y todos son falsos para el string vacío. Un espacio hace que isalpha sea falso.

Validar una edad antes de convertirla

Se requiere leer una edad y evitar que el programa falle si el usuario escribe letras.


edad = input("Tu edad: ").strip()

if edad.isdigit():
    print("Edad:", int(edad))
else:
    print("Eso no es un número.")
Patrón

Preguntar antes de convertir evita el error de ejecución que produce int con un texto que no es numérico.

f-strings

Definición

Una f-string inserta el valor de una variable dentro de un texto. Se escribe poniendo una f antes de la comilla.


nombre = "Ana"
edad = 22

print(f"Hola, {nombre}. Tienes {edad} años.")
# Hola, Ana. Tienes 22 años.

Con y sin f-string

Con concatenación


print("El área es " +
      str(base * altura) +
      " cm2")

Con f-string


print(f"El área es {base * altura} cm2")
Ventaja

La f-string no necesita convertir con str ni cerrar y abrir comillas, así que se lee de corrido.

Expresiones dentro de una f-string

Entre las llaves cabe cualquier expresión, no solo el nombre de una variable.


a = 5
b = 3

print(f"La suma de {a} y {b} es {a + b}")
print(f"El cuadrado de {a} es {a ** 2}")
print(f"En mayúsculas: {nombre.upper()}")

Dar formato a un número

Después de dos puntos se indica cómo mostrar el valor.


precio = 1234.5678

print(f"Total: {precio:.2f}")    # Total: 1234.57
print(f"Total: {precio:10.2f}")  # alineado a 10 espacios
Uso típico

Mostrar dinero con dos decimales y alinear columnas en una tabla impresa en la terminal.

Analizador de texto

Se requiere leer una frase y reportar cuántos caracteres y cuántas palabras tiene, mostrarla en mayúsculas e indicar si menciona Python. Los espacios sobrantes de la entrada no deben contarse.


texto = input("Escribe una frase: ")
limpio = texto.strip()

print(f"Caracteres: {len(limpio)}")
print(f"Palabras: {len(limpio.split())}")
print(f"Mayúsculas: {limpio.upper()}")
print(f"Menciona Python: {'Python' in limpio}")

texto = input("Escribe una frase: ")
limpio = texto.strip()

print(f"Caracteres: {len(limpio)}")
print(f"Palabras: {len(limpio.split())}")
print(f"Mayúsculas: {limpio.upper()}")
print(f"Menciona Python: {'Python' in limpio}")
texto = input(...)

La función input siempre devuelve un string, incluso si el usuario escribe números. Lo que llega puede traer espacios al inicio o al final.


texto = input("Escribe una frase: ")
limpio = texto.strip()

print(f"Caracteres: {len(limpio)}")
print(f"Palabras: {len(limpio.split())}")
print(f"Mayúsculas: {limpio.upper()}")
print(f"Menciona Python: {'Python' in limpio}")
limpio = texto.strip()

strip devuelve un string nuevo sin los espacios de los extremos. El resultado se guarda en otra variable porque el original no cambia.


texto = input("Escribe una frase: ")
limpio = texto.strip()

print(f"Caracteres: {len(limpio)}")
print(f"Palabras: {len(limpio.split())}")
print(f"Mayúsculas: {limpio.upper()}")
print(f"Menciona Python: {'Python' in limpio}")
{len(limpio)}

Dentro de las llaves se puede llamar a una función. len cuenta los caracteres del texto ya limpio, no los de la entrada original.


texto = input("Escribe una frase: ")
limpio = texto.strip()

print(f"Caracteres: {len(limpio)}")
print(f"Palabras: {len(limpio.split())}")
print(f"Mayúsculas: {limpio.upper()}")
print(f"Menciona Python: {'Python' in limpio}")
{len(limpio.split())}

split corta el texto en palabras y len cuenta cuántas quedaron. Se leen de adentro hacia afuera, primero el corte y luego la cuenta.


texto = input("Escribe una frase: ")
limpio = texto.strip()

print(f"Caracteres: {len(limpio)}")
print(f"Palabras: {len(limpio.split())}")
print(f"Mayúsculas: {limpio.upper()}")
print(f"Menciona Python: {'Python' in limpio}")
{limpio.upper()}
{'Python' in limpio}

Una f-string también acepta métodos y comparaciones. La última línea imprime True o False según si la palabra aparece en la frase.

Salida del analizador

Para la entrada con espacios sobrantes Aprendo Python.


Caracteres: 14
Palabras: 2
Mayúsculas: APRENDO PYTHON
Menciona Python: True
Nótese

Son 14 caracteres y no 18, porque strip quitó los espacios de los extremos antes de contar.

Validador de correo

Se requiere revisar un correo escrito por el usuario. Debe contener el símbolo arroba, terminar en un dominio aceptado y, si cumple, mostrar el usuario y el dominio por separado. La entrada se normaliza antes de revisarla.


correo = input("Correo electrónico: ").strip().lower()

if "@" not in correo:
    print("Falta el símbolo arroba")
elif not correo.endswith(".com") and not correo.endswith(".gt"):
    print("Dominio no reconocido")
else:
    partes = correo.split("@")
    print(f"Usuario: {partes[0]}")
    print(f"Dominio: {partes[1]}")

correo = input("Correo electrónico: ").strip().lower()

if "@" not in correo:
    print("Falta el símbolo arroba")
elif not correo.endswith(".com") and not correo.endswith(".gt"):
    print("Dominio no reconocido")
else:
    partes = correo.split("@")
    print(f"Usuario: {partes[0]}")
    print(f"Dominio: {partes[1]}")
.strip().lower()

Los métodos se encadenan porque cada uno devuelve un string. strip actúa sobre lo que dio input y lower sobre lo que dio strip.


correo = input("Correo electrónico: ").strip().lower()

if "@" not in correo:
    print("Falta el símbolo arroba")
elif not correo.endswith(".com") and not correo.endswith(".gt"):
    print("Dominio no reconocido")
else:
    partes = correo.split("@")
    print(f"Usuario: {partes[0]}")
    print(f"Dominio: {partes[1]}")
if "@" not in correo:

Se descarta primero el caso más grave. Sin arroba el correo no se puede dividir, así que no tiene sentido seguir revisando.


correo = input("Correo electrónico: ").strip().lower()

if "@" not in correo:
    print("Falta el símbolo arroba")
elif not correo.endswith(".com") and not correo.endswith(".gt"):
    print("Dominio no reconocido")
else:
    partes = correo.split("@")
    print(f"Usuario: {partes[0]}")
    print(f"Dominio: {partes[1]}")
not correo.endswith(".com")
and not correo.endswith(".gt")

endswith devuelve un booleano, así que se combina con los operadores lógicos ya conocidos. La condición se cumple cuando no termina en ninguno de los dos dominios.


correo = input("Correo electrónico: ").strip().lower()

if "@" not in correo:
    print("Falta el símbolo arroba")
elif not correo.endswith(".com") and not correo.endswith(".gt"):
    print("Dominio no reconocido")
else:
    partes = correo.split("@")
    print(f"Usuario: {partes[0]}")
    print(f"Dominio: {partes[1]}")
partes = correo.split("@")

Esta línea solo se ejecuta cuando ya se sabe que hay un arroba. El corte produce dos partes, la que queda antes y la que queda después.


correo = input("Correo electrónico: ").strip().lower()

if "@" not in correo:
    print("Falta el símbolo arroba")
elif not correo.endswith(".com") and not correo.endswith(".gt"):
    print("Dominio no reconocido")
else:
    partes = correo.split("@")
    print(f"Usuario: {partes[0]}")
    print(f"Dominio: {partes[1]}")
{partes[0]}
{partes[1]}

La posición cero es el usuario y la uno el dominio. A diferencia del slice escrito a mano, esto funciona con cualquier correo.

Casos de prueba del validador

EntradaSalida
[email protected]Usuario jose, dominio uvg.edu.gt
[email protected] Usuario ana, dominio gmail.com
jose.uvg.edu.gtFalta el símbolo arroba
[email protected]Dominio no reconocido
Práctica

Probar un programa con entradas mal escritas es parte de escribirlo, no un paso opcional al final.

Contador de vocales y consonantes

Se requiere recorrer una palabra y reportar cuántas vocales y cuántas consonantes tiene. Los acentos cuentan como vocales y los caracteres que no son letras se ignoran.


palabra = input("Escribe una palabra: ").lower()
vocales = "aeiouáéíóú"
total_vocales = 0
total_consonantes = 0

for letra in palabra:
    if letra in vocales:
        total_vocales = total_vocales + 1
    elif letra.isalpha():
        total_consonantes = total_consonantes + 1

print(f"Vocales: {total_vocales}")
print(f"Consonantes: {total_consonantes}")

palabra = input("Escribe una palabra: ").lower()
vocales = "aeiouáéíóú"
total_vocales = 0
total_consonantes = 0

for letra in palabra:
    if letra in vocales:
        total_vocales = total_vocales + 1
    elif letra.isalpha():
        total_consonantes = total_consonantes + 1

print(f"Vocales: {total_vocales}")
print(f"Consonantes: {total_consonantes}")
.lower()
vocales = "aeiouáéíóú"

Pasar la palabra a minúsculas evita tener que listar también las vocales en mayúscula. El string de vocales hace de referencia para la comparación.


palabra = input("Escribe una palabra: ").lower()
vocales = "aeiouáéíóú"
total_vocales = 0
total_consonantes = 0

for letra in palabra:
    if letra in vocales:
        total_vocales = total_vocales + 1
    elif letra.isalpha():
        total_consonantes = total_consonantes + 1

print(f"Vocales: {total_vocales}")
print(f"Consonantes: {total_consonantes}")
total_vocales = 0
total_consonantes = 0

Los contadores se inicializan antes del ciclo. Si se declararan dentro, se reiniciarían en cada vuelta y el resultado final sería cero o uno.


palabra = input("Escribe una palabra: ").lower()
vocales = "aeiouáéíóú"
total_vocales = 0
total_consonantes = 0

for letra in palabra:
    if letra in vocales:
        total_vocales = total_vocales + 1
    elif letra.isalpha():
        total_consonantes = total_consonantes + 1

print(f"Vocales: {total_vocales}")
print(f"Consonantes: {total_consonantes}")
for letra in palabra:

El ciclo da una vuelta por carácter y no necesita índices ni la longitud de la palabra. La variable letra contiene un string de un solo carácter.


palabra = input("Escribe una palabra: ").lower()
vocales = "aeiouáéíóú"
total_vocales = 0
total_consonantes = 0

for letra in palabra:
    if letra in vocales:
        total_vocales = total_vocales + 1
    elif letra.isalpha():
        total_consonantes = total_consonantes + 1

print(f"Vocales: {total_vocales}")
print(f"Consonantes: {total_consonantes}")
if letra in vocales:
elif letra.isalpha():

El elif se evalúa solo cuando la letra no es vocal. isalpha descarta espacios, guiones y números, que no se cuentan en ningún grupo.

Salida del contador

Para la entrada murciélago.


Vocales: 5
Consonantes: 5
Nótese

La vocal acentuada se cuenta porque está en el string de referencia. Sin ella el resultado sería cuatro vocales y una letra sin clasificar.

Modificar un carácter directamente


texto = "Hola"
texto[0] = "h"   # TypeError
Corrección

Los strings son inmutables, por lo que se construye uno nuevo con la letra deseada más un slice del resto.

No guardar el resultado del método


nombre = "  carlos  "
nombre.strip()

print(nombre)   # "  carlos  "
Corrección

La línea debe escribirse como nombre igual a nombre punto strip. Es el error más frecuente al trabajar con strings y no produce ningún mensaje de error.

Índice fuera de rango


texto = "Hola"
print(texto[4])   # IndexError
Corrección

El último índice válido es tres. Para el último carácter conviene usar menos uno, que nunca se pasa.

Comparar sin normalizar


respuesta = input("¿Continuar? (si/no): ")

if respuesta == "si":
    print("Continuando...")
Corrección

Si el usuario escribe Si o deja un espacio, la comparación falla en silencio. Se corrige aplicando strip y lower antes de comparar.

Confundir el resultado de find


texto = "El gato"

if texto.find("perro"):
    print("Encontrado")   # se imprime
Corrección

find devuelve menos uno, que Python considera verdadero. Se compara contra menos uno o se usa el operador in.

Resumen de operaciones

OperaciónPara qué sirve
len(texto)Cuántos caracteres tiene
texto[i]Obtener un carácter
texto[a:b]Extraer una porción
for letra in textoRecorrerlo carácter por carácter
parte in textoSaber si contiene un texto
f"{variable}"Insertar valores en un mensaje

Resumen de métodos

MétodoDevuelve
upper, lower, titleEl texto con otro formato
stripEl texto sin espacios en los extremos
replaceEl texto con una parte cambiada
find, countUna posición o una cantidad
startswith, endswith, isdigitUn booleano
split, joinVarias partes o un solo texto

Buenas prácticas

Limpiar con strip toda entrada del usuario
Guardar siempre el resultado de un método
Preferir f-strings sobre la concatenación
Validar antes de convertir con int
Lo que sigue

split entrega sus partes en una lista, la estructura que permite guardar muchos valores en una sola variable y el tema de la próxima clase.