Este tutorial adapta pedagógicamente el Día 8. Las secciones 📝 Ejercicio original del curso provienen de los archivos del curso. Los retos 🟢🟡🟠🔴, el proyecto extra y el proyecto integrador son creaciones de esta adaptación. Las correcciones al material original aparecen como 🛠️ Nota técnica.
Tabla de contenidos
- Antes de empezar: mensajes secretos
- Funciones con entradas: parámetros y argumentos
- Varias entradas: argumentos posicionales y por palabra clave
- Cifrado César, parte 1: cifrar (
index()y%) - Cifrado César, parte 2: descifrar y unificar en una sola función
- Cifrado César, parte 3: caracteres especiales, repetir y depurar
- 🚀 Proyecto del día: el programa César completo
- 🌟 Proyecto extra: Rompe el código (ataque de fuerza bruta)
- 🏆 Proyecto integrador del Día 8: Cifrado de Vigenère
- 🤖 Programar con apoyo de IA
- 🛠️ Correcciones técnicas al material original
- 📋 Matriz de trazabilidad
- 📦 Evidencias de aprendizaje del Día 8
0. Antes de empezar: mensajes secretos
(Fuente: 060 - Day 8 Goals- what we will make by the end of the day.md, 066 - How You Can -Stay- Motivated.md)
Según la historia, Julio César enviaba sus mensajes militares desplazando cada letra un número fijo de posiciones en el alfabeto. Con un desplazamiento de 3, la A se convierte en D, la B en E, y así sucesivamente. Quien conoce el número puede deshacer el cambio. Hoy programaremos ese cifrado César. Para lograrlo, necesitamos funciones que reciban datos: el texto, el desplazamiento y si se debe cifrar o descifrar.
Mensaje de cierre del curso: en algún momento tu motivación va a bajar. Escribe por qué estás aprendiendo a programar y ponlo en un lugar visible.
Prerequisito general: funciones sin parámetros (Día 6), listas e índices (Día 4),
%(Día 3) y bucles (Días 5 y 6).
1. Funciones con entradas: parámetros y argumentos
(Fuente: 061 - Functions with Inputs.md)
Prerequisito: definir y llamar funciones (Día 6).
🎯 Objetivo de aprendizaje
- Definir funciones que reciben datos.
- Distinguir entre parámetro y argumento.
📖 Explicación conceptual
Una función sin entradas hace siempre lo mismo:
def saludar():
print("Hola")
print("¿Cómo estás?")
print("¿Qué tal el clima?")¿Y si quisiéramos saludar a cada persona por su nombre? Hay que darle a la función un dato de entrada:
def saludar_con_nombre(nombre): # nombre es el PARÁMETRO
print(f"Hola {nombre}")
print(f"¿Cómo estás, {nombre}?")
saludar_con_nombre("Angela") # "Angela" es el ARGUMENTO
saludar_con_nombre("Jack Bauer")Cuando se llama la función, Python hace algo equivalente a nombre = "Angela" dentro de la función.
| Término | Qué es | En el ejemplo |
|---|---|---|
| Parámetro | El nombre que recibe el dato dentro de la función | nombre |
| Argumento | El valor real que se envía al llamar la función | "Angela" |
Analogía del curso: una memoria USB. El computador (la función) es el mismo, pero muestra archivos distintos según la memoria (el argumento) que conectes.
En internet, a veces se usan "parámetro" y "argumento" como si fueran sinónimos. Lo importante es que tú conozcas la diferencia.
⚠️ Errores frecuentes
- Llamar la función sin argumento:
saludar_con_nombre()produceTypeError: missing 1 required positional argument: 'nombre'. - Enviar argumentos de más:
saludar_con_nombre("Ana", "Luis")produceTypeError: takes 1 positional argument but 2 were given. - Usar el parámetro fuera de la función:
print(nombre)fuera de ella produceNameError. El parámetro solo existe dentro de la función.
📝 Ejercicio original del curso: la función greet
Enunciado:
- Crea
greet()con tresprint()y llámala. - Crea
greet_with_name(name)que use el nombre en los mensajes (con f-strings) y llámala con distintos nombres.
Antes de ejecutar: predice qué se imprimirá con greet_with_name("Angela").
Retos adicionales (creados para esta adaptación)
- 🟢 Reto 1:
mostrar_tabla(numero)imprime la tabla de multiplicar del número que recibe. - 🟡 Reto 2:
dibujar_linea(largo)imprime una línea de-del largo indicado. Úsala para enmarcar un título. - 🟠 Reto 3:
verificar_contrasena(clave)imprime si la clave es "débil" (menos de 8 caracteres) o "aceptable". Llámala con 3 claves distintas. - 🔴 Reto 4: revisa tus proyectos de los días anteriores (la Caja Registradora del Día 6 o el Ahorcado del Día 7) y encuentra un bloque de código que se repita con pequeñas variaciones. Conviértelo en una función con parámetro.
🧩 Comprueba lo aprendido: Tema 1
- Conceptual: en
def area(base, altura):yarea(4, 5), señala los parámetros y los argumentos. - Predicción: ¿qué imprime este código?
def doble(x):
print(x * 2)
doble(3)
doble("ja")- Depuración: corrige
def saludar(nombre): print(f"Hola {nombre}")seguido de la llamadasaludar().
2. Varias entradas: argumentos posicionales y por palabra clave
(Fuente: 062 - Positional vs. Keyword Arguments.md)
🎯 Objetivo de aprendizaje
- Definir funciones con varios parámetros.
- Usar argumentos posicionales y argumentos por palabra clave (keyword arguments), y elegir el adecuado.
📖 Explicación conceptual
def saludar_con(nombre, ubicacion):
print(f"Hola {nombre}")
print(f"¿Cómo es la vida en {ubicacion}?")Argumentos posicionales. Se asignan por orden: el primer argumento va al primer parámetro, el segundo al segundo.
saludar_con("Jack Bauer", "Nowhere") # ✅
saludar_con("Nowhere", "Jack Bauer") # ❌ "Hola Nowhere" / "¿Cómo es la vida en Jack Bauer?"Argumentos por palabra clave. Se indica el parámetro al que va cada valor, así que el orden deja de importar:
saludar_con(ubicacion="Londres", nombre="Angela") # ✅ funciona igual| Tipo | Ventaja | Desventaja |
|---|---|---|
| Posicional | Más corto | Es fácil equivocarse con el orden |
| Por palabra clave | Más claro y menos propenso a errores | Las líneas quedan más largas |
El curso recomienda usar tu criterio: con 1 o 2 parámetros obvios, los argumentos posicionales bastan; con muchos parámetros, o cuando el orden no es evidente, conviene usar palabras clave.
⚠️ Errores frecuentes
- Poner un argumento posicional después de uno por palabra clave:
saludar_con(nombre="Ana", "Cali")produceSyntaxError: positional argument follows keyword argument. - Escribir mal el nombre del parámetro:
saludar_con(nombres="Ana", ubicacion="Cali")produceTypeError: got an unexpected keyword argument 'nombres'.
📝 Ejercicio original del curso: llamar con palabras clave
Enunciado: llama a greet_with(name, location) usando argumentos por palabra clave y comprueba que el resultado no cambia si inviertes el orden.
La lección termina remitiendo a "un ejercicio de codificación" en la lección siguiente. Su enunciado no está incluido entre los archivos suministrados.
Retos adicionales (creados para esta adaptación)
- 🟢 Reto 1:
presentar(nombre, curso, edad). Llámala de las dos formas. - 🟡 Reto 2:
calcular_imc(peso, estatura). Llámala con los argumentos invertidos por posición y explica el resultado absurdo. Luego corrígelo con palabras clave. - 🟠 Reto 3:
precio_final(precio, descuento, iva)que imprime el precio con descuento e IVA. Escribe 3 llamadas y verifica los resultados a mano. - 🔴 Reto 4: investiga los valores por defecto (
def saludar(nombre, saludo="Hola"):) en la documentación oficial. ¿Qué problema resuelven? Escribe un ejemplo propio.
3. Cifrado César, parte 1: cifrar
(Fuente: 063 - Caesar Cipher Part 1 - Encryption.md)
Prerequisito: Temas 1 y 2,
%(Día 3) y listas (Día 4).
🎯 Objetivo de aprendizaje
- Encontrar la posición de un elemento en una lista con
.index(). - Usar
%para "dar la vuelta" al alfabeto. - Construir la función
encrypt(original_text, shift_amount).
📖 Explicación conceptual
El método .index() devuelve la posición de un elemento en una lista:
frutas = ["manzana", "pera", "naranja"]
frutas.index("pera") # 1El algoritmo, letra por letra. Ejemplo: "hello" con desplazamiento 2.
| Letra | alphabet.index(letra) |
+ desplazamiento | Nueva letra |
|---|---|---|---|
| h | 7 | 9 | j |
| e | 4 | 6 | g |
| l | 11 | 13 | n |
| l | 11 | 13 | n |
| o | 14 | 16 | q |
Resultado: jgnnq.
El problema del final del alfabeto. Si ciframos z (posición 25) con desplazamiento 9, la nueva posición sería 34, que no existe: se produce IndexError. La solución del curso es usar el módulo con la longitud del alfabeto (26):
posicion_desplazada %= len(alphabet) # 34 % 26 = 8 → "i"El residuo siempre queda entre 0 y 25. Es como un reloj: después de la última posición se vuelve a empezar desde la primera.
🛠️ Nota técnica: en el video, el módulo se explica con 25 ("34 % 25 = 9"). Pero el alfabeto tiene 26 letras y el código usa
len(alphabet), que es 26:34 % 26 = 8, que corresponde a la letrai. Es justo el resultado que el propio video anuncia ("debería darnos i"). Con 25 el resultado sería incorrecto.
Estructura de la solución del curso:
def encrypt(original_text, shift_amount):- Un acumulador
cipher_text = ""fuera delfor. - Por cada letra: posición → posición + desplazamiento →
%→ letra nueva → acumular. - Después del
for: imprimir el resultado. - Llamar la función con argumentos por palabra clave:
encrypt(original_text=text, shift_amount=shift).
Consejo del curso: imprime los valores intermedios (posición, nueva posición, letra) mientras programas, para ver qué ocurre "entre bastidores".
📝 Ejercicio original del curso: TODO de la parte 1
- Crear
encryptcon los parámetrosoriginal_textyshift_amount. - Dentro de ella, desplazar cada letra hacia adelante e imprimir el texto cifrado.
- Llamarla con las entradas del usuario.
- Resolver el caso de
zcon desplazamiento 9 (IndexError).
El archivo inicial del curso (con la lista
alphabety las tres entradas) no está incluido entre los materiales suministrados. Creaalphabet = ["a", "b", ..., "z"]. Pista:list("abcdefghijklmnopqrstuvwxyz")crea esa misma lista en una sola línea.
🔍 Antes de programar
- Cifra a mano
holacon desplazamiento 3. - ¿Qué valor debe dar tu programa para
xyzcon desplazamiento 3? (Respuesta:abc.) - El curso menciona que hay varias soluciones para el problema del final del alfabeto. Piensa al menos en una distinta al módulo.
Retos adicionales (creados para esta adaptación)
- 🟢 Reto 1: cifra
abccon desplazamiento 29. ¿Qué resultado da? ¿Por qué es igual al de desplazamiento 3? - 🟡 Reto 2: resuelve el problema del final del alfabeto sin
%, usando unif. Compara ambas soluciones. - 🟠 Reto 3: haz que
encryptimprima una tabla de seguimiento como la de la explicación (letra, posición, nueva posición, letra nueva) antes del resultado final. (En el Día 10 aprenderás a hacer que una función devuelva su resultado en lugar de imprimirlo.) - 🔴 Reto 4: el alfabeto del curso no incluye la ñ. ¿Qué pasaría con
"niño"? Modifica la lista para incluirla. ¿Qué cambia en el%? ¿Pueden comunicarse ahora dos personas que usen alfabetos distintos?
4. Cifrado César, parte 2: descifrar y unificar
(Fuente: 064 - Caesar Cipher Part 2 - Decryption.md)
🎯 Objetivo de aprendizaje
- Construir
decrypte identificar que es casi igual aencrypt. - Eliminar el código repetido combinando ambas en una sola función
caesar.
📖 Explicación conceptual
Descifrar es desplazar hacia atrás: posición - desplazamiento. El % también funciona con números negativos en Python: (0 - 2) % 26 da 24, que es la y. Así, descifrar a con 2 da y.
Código repetido → una sola función. encrypt y decrypt solo difieren en una operación: + o -. El curso aprovecha un truco matemático: sumar un número negativo es lo mismo que restar.
def caesar(original_text, shift_amount, encode_or_decode):
if encode_or_decode == "decode":
shift_amount *= -1
# ...el mismo bucle de encrypt, siempre con +Cuidado con los nombres (sombreado de variables). Si el parámetro se llamara direction, igual que la variable global donde se guarda la respuesta del usuario, PyCharm advierte: "Shadows name 'direction' from outer scope". El código funciona, pero es confuso. Por eso el curso lo llama encode_or_decode. *(El ámbito o *scope* se estudia a fondo en el Día 12.)*
Truco del mensaje final. En inglés, encode + d = encoded y decode + d = decoded, así que el curso escribe f"Here is the {encode_or_decode}d result".
🛠️ Nota para la versión en español: ese truco depende del inglés. Con "codificar"/"decodificar" no funciona agregar una letra. Usa un
ifpara elegir el mensaje, o nombra las opciones de modo que el truco funcione (por ejemplo"cifrado"/"descifrado", y escribef"Resultado {modo}:").
📝 Ejercicio original del curso: TODO de la parte 2
- Crear
decrypt(original_text, shift_amount). - Desplazar cada letra hacia atrás e imprimir el resultado.
- Combinar ambas en
caesar(original_text, shift_amount, encode_or_decode).
Recomendación del curso: hazlo en orden. No saltes al paso 3 sin entender cómo se diferencia decrypt de encrypt.
Retos adicionales (creados para esta adaptación)
- 🟢 Reto 1: comprueba que cifrar y luego descifrar con el mismo desplazamiento devuelve el texto original, con 5 palabras distintas.
- 🟡 Reto 2: descifrar con desplazamiento
nes lo mismo que cifrar con26 - n. Verifícalo y explica por qué. - 🟠 Reto 3: reescribe
caesarsin*= -1, usandoif/elsepara sumar o restar. ¿Cuál versión es más legible? - 🔴 Reto 4: el ROT13 es un César con desplazamiento 13. ¿Por qué con ROT13 la misma operación sirve para cifrar y para descifrar? Demuéstralo con código.
5. Cifrado César, parte 3: caracteres especiales, repetir y depurar
(Fuente: 065 - Caesar Cipher Part 3 - Reorganising our Code.md)
🎯 Objetivo de aprendizaje
- Conservar sin cambios los caracteres que no son letras (espacios, números, símbolos).
- Repetir el programa con una bandera
should_continue. - Encontrar un error mediante pruebas.
📖 Explicación conceptual
Caracteres especiales. Si el carácter no está en alphabet, se agrega tal cual:
if letter not in alphabet:
output_text += letter
else:
# desplazar como antesOtra opción que menciona el curso es agregar números y símbolos a la lista alphabet. Es más difícil, porque hay que prever todos los símbolos posibles.
Repetir el programa. El mismo patrón de bandera del Día 7:
should_continue = True
while should_continue:
# pedir datos y llamar caesar(...)
restart = input("Escribe 'si' para continuar, o 'no' para salir:\n").lower()
if restart == "no":
should_continue = False
print("Adiós")🧪 El error que se encuentra probando (actividad central del curso)
El curso pide probar repetidamente hasta encontrar un error. Lo que ocurre:
- Cifrar
abcon desplazamiento 2 →cd✅ - Descifrar
cdcon desplazamiento 2 → se esperaab, pero daaf❌ (resultado verificado).
Causa: la línea shift_amount *= -1 quedó dentro del for. Entonces el signo se invierte en cada letra: la primera letra se desplaza hacia atrás, la segunda hacia adelante, la tercera otra vez hacia atrás…
Corrección: mover esa línea antes del for. Es otra vez el tema del Día 5: lo que debe pasar una sola vez va fuera del bucle.
📝 Ejercicio original del curso: TODO de la parte 3
- Importar e imprimir
logodesdeart.py(archivo no incluido entre los materiales: crea tu propio logo en arte ASCII). - Conservar los números, los símbolos y los espacios.
- Preguntar si se quiere repetir el programa y salir con "no".
Retos adicionales (creados para esta adaptación)
- 🟢 Reto 1: haz que el programa conserve las mayúsculas:
Hola→Krod. (Pista:.isupper()y.lower()/.upper().) - 🟡 Reto 2: valida que el desplazamiento sea un número y que la opción sea exactamente "encode" o "decode". Si no, vuelve a pedirla con un
while. - 🟠 Reto 3: muestra al final cuántos mensajes se procesaron en la sesión.
- 🔴 Reto 4: diseña 5 casos de prueba que habrían detectado el error de
*= -1desde el principio. ¿Por qué un caso de una sola letra no lo detecta?
6. 🚀 Proyecto del día: el programa César completo
(Fuente: archivos 063–065, proyecto oficial del curso original)
Requisitos funcionales
- Mostrar un logo al inicio.
- Preguntar:
encodeodecode, el mensaje y el desplazamiento. - Una sola función
caesar(original_text, shift_amount, encode_or_decode). - Conservar los caracteres que no están en el alfabeto.
- Soportar cualquier desplazamiento (incluidos los mayores de 26) gracias a
%. - Repetir hasta que el usuario escriba "no".
🔍 Antes de programar
- ¿Qué partes van dentro de la función y cuáles fuera (entradas del usuario, bucle de repetición)?
- ¿Qué instrucciones deben ejecutarse una sola vez por llamada y cuáles una vez por letra?
Pruebas
| Modo | Texto | Desplazamiento | Resultado esperado |
|---|---|---|---|
| encode | hello | 2 | jgnnq |
| encode | z | 9 | i |
| decode | cd | 2 | ab |
| decode | a | 2 | y |
| encode | hola mundo 123! | 3 | krod pxqgr 123! |
| decode | krod pxqgr 123! | 3 | hola mundo 123! |
| encode | abc | 29 | def |
⭐ Extensión del proyecto
- Soportar mayúsculas y la ñ.
- Mostrar el mensaje cifrado en bloques de 5 letras (como en la criptografía clásica).
- Reflexión: ¿es seguro el cifrado César? (Pista: ¿cuántas claves posibles hay? Ver el proyecto extra.)
7. 🌟 Proyecto extra: Rompe el código
Situación
Interceptaste el mensaje khoor. Sabes que usa el cifrado César, pero no conoces el desplazamiento. Como solo hay 25 desplazamientos útiles, puedes probarlos todos: eso es un ataque de fuerza bruta.
Requisitos
- Reutilizar tu función
caesarsin modificarla. Esa es una de las ventajas de tener funciones. - Un bucle
forconrange(1, 26)que, para cada desplazamiento, imprima:Desplazamiento 3: hello. - El usuario lee la lista e identifica el mensaje legible.
Resultado verificado: con khoor, el desplazamiento 3 da hello.
⭐ Extensión (pensamiento computacional)
¿Puede el programa adivinar solo cuál es el mensaje correcto? Idea: cuenta en cada resultado cuántas letras son vocales, o cuántas palabras aparecen en una pequeña lista de palabras comunes del español ("el", "la", "de", "que"…). Elige el desplazamiento con la puntuación más alta. Esta es la base del análisis de frecuencias, la técnica que se usó históricamente para romper cifrados.
Reflexión
Si romper el cifrado César es tan fácil, ¿por qué es importante estudiarlo? ¿Qué harías para hacerlo más difícil de romper? (Ver el proyecto integrador.)
8. 🏆 Proyecto integrador del Día 8: Cifrado de Vigenère
Proyecto integrador creado para esta adaptación. Es una versión más robusta del cifrado César. Integra funciones con varios parámetros, listas,
index(),%, bucles y validación.
Situación problema
El cifrado César se rompe probando 25 claves. En el siglo XVI se popularizó el cifrado de Vigenère, que en lugar de un solo desplazamiento usa una palabra clave: cada letra de la clave indica un desplazamiento distinto (a = 0, b = 1, …, z = 25) y la clave se repite a lo largo del mensaje.
Ejemplo clásico (verificado): mensaje attackatdawn, clave lemon → lxfopvefrnhr.
| Mensaje | a | t | t | a | c | k | a | t | d | a | w | n |
|---|---|---|---|---|---|---|---|---|---|---|---|---|
| Clave (se repite) | l | e | m | o | n | l | e | m | o | n | l | e |
| Desplazamiento | 11 | 4 | 12 | 14 | 13 | 11 | 4 | 12 | 14 | 13 | 11 | 4 |
| Resultado | l | x | f | o | p | v | e | f | r | n | h | r |
Pregunta orientadora
¿Cómo reutilizar las ideas del César (posición, desplazamiento y %) para construir un cifrado mucho más difícil de romper?
Requerimientos
- Función
vigenere(texto, clave, modo)que cifre y descifre. - La posición en la clave se calcula con
%: el carácteridel mensaje usa la letra de la clave en la posicióni % len(clave). - Decisión de diseño: ¿la clave avanza también con los espacios y símbolos o solo con las letras? Justifícala y documéntala en un comentario.
- Validar que la clave solo tenga letras.
- Menú que se repite, igual que en el César.
Etapas
- Recorrer el mensaje con un índice (
for i in range(len(texto))) y mostrar la letra de la clave que le corresponde a cada posición. - Cifrar.
- Descifrar (reutiliza el truco
* -1del César). - Caracteres especiales y validación.
Entregables
Código funcional, tabla de pruebas y un párrafo que compare la seguridad del César con la de Vigenère.
Criterios técnicos
vigenere("attackatdawn", "lemon", "encode")producelxfopvefrnhr.- Descifrar el resultado devuelve el texto original.
- No se produce
IndexErrorcon claves más largas o más cortas que el mensaje.
Posibles extensiones
Investiga cómo se rompió Vigenère en el siglo XIX (el método Kasiski) y por qué hoy tampoco se considera seguro.
9. 🤖 Programar con apoyo de IA
El curso muestra el valor de probar para encontrar errores: el problema del *= -1 no se ve leyendo el código, sino ejecutando casos.
Actividad: entrega a una IA tu función caesar con el error (*= -1 dentro del for) y pregúntale si tiene algún error. Luego:
- ¿Lo encontró? ¿Lo explicó bien?
- Verifica su corrección con tu tabla de pruebas.
- Pídele también casos de prueba. ¿Incluye alguno de varias letras en modo decode? Ese es el que revela el error.
Pregunta de ética: una IA puede romper un cifrado César en segundos. ¿Qué significa eso para la seguridad de la información? ¿Qué cifrados usan hoy las aplicaciones de mensajería?
10. 🛠️ Correcciones técnicas al material original
| Archivo | Afirmación en la transcripción | Qué ocurre realmente | Tratamiento |
|---|---|---|---|
063 |
El módulo se explica con 25 ("34 % 25 = 9") | El alfabeto tiene 26 letras: 34 % 26 = 8 → i |
Nota técnica, Tema 3 |
063 |
index se llama "función incorporada" |
Es un método de las listas: lista.index(x) |
Tema 3 |
064 |
El truco {encode_or_decode}d |
Funciona solo en inglés | Nota para la versión en español, Tema 4 |
065 |
El resultado erróneo "una f" | El resultado verificado del error es af en lugar de ab |
Tema 5 |
063–065 |
Archivos iniciales (alphabet, art.py) |
No están incluidos entre los materiales suministrados | Se pide crearlos |
| — | Seguridad del cifrado César | No es seguro: solo hay 25 claves útiles | Proyecto extra |
11. 📋 Matriz de trazabilidad
| Contenido original | Archivo de origen | Concepto desarrollado | Ejercicio original | Reto adicional | Proyecto relacionado |
|---|---|---|---|---|---|
| Objetivos: cifrado César | 060 |
Sección 0 | — | — | Sección 6 |
| Funciones con entradas, parámetro frente a argumento | 061 |
Tema 1 | greet y greet_with_name |
Retos 1–4 del Tema 1 | Todos |
| Varias entradas, posicionales frente a palabra clave | 062 |
Tema 2 | Llamar con palabras clave. Ejercicio posterior (mencionado, no suministrado) | Retos 1–4 del Tema 2 (valores por defecto) | Secciones 6 y 8 |
Cifrar, index(), % |
063 |
Tema 3 | TODO 1–4 de la parte 1 | Retos 1–4 del Tema 3 (ñ) | Secciones 6, 7 y 8 |
| Descifrar, unificar, sombreado de nombres | 064 |
Tema 4 | TODO 1–3 de la parte 2 | Retos 1–4 del Tema 4 (ROT13) | Secciones 6 y 8 |
Caracteres especiales, repetición, error de *= -1 |
065 |
Tema 5 | TODO 1–3 de la parte 3 y búsqueda del error | Retos 1–4 del Tema 5 | Sección 6 |
| Motivación | 066 |
Sección 0 | — | — | — |
| (No existe en el curso original) | — | — | — | Rompe el código (fuerza bruta) | Sección 7 |
| (No existe en el curso original) | — | — | — | Cifrado de Vigenère | Sección 8 |
12. 📦 Evidencias de aprendizaje del Día 8
- Programa César completo que pasa la tabla de 7 pruebas.
- Explicación escrita, con tus palabras, del error de
*= -1y de por qué ocurre. - Tabla de parámetros y argumentos (Tema 1) y ejemplo del error por invertir argumentos posicionales (Reto 2 del Tema 2).
- Proyecto extra (fuerza bruta) o integrador (Vigenère).
- Cuaderno de errores:
TypeError: missing required positional argument,SyntaxError: positional argument follows keyword argument,IndexErroral final del alfabeto y la instrucción que debía ir fuera del bucle.