Setup. Una transcripción de call-center de telco tiene fácilmente 3 000 palabras; un histórico de demanda de Inditex, cientos de semanas. Para que una RNN conecte la palabra 1 con la palabra T, la información atraviesa T−1 multiplicaciones recurrentes. Arriba pinto la señal superviviente Π|wl| en escala log (curva tinta: cadena con ganancias aleatorias de media w; discontinua gris: el caso ideal wt), contra la línea dorada de la atención, que siempre vale 1 porque conecta cualquier par en un paso. Abajo, el dibujo de las dos rutas sobre la frase.
Juega. Mueve w a ambos lados de 1 y estira T. Con w < 1 el cliente dijo «quiero darme de baja» al principio de la llamada y al final la red ya no lo recuerda; con w > 1 las activaciones revientan antes de llegar. La banda útil alrededor de w = 1 se estrecha al crecer T.
Lee así. El eje y es logarítmico: una recta descendente es extinción exponencial. La distancia vertical entre la curva tinta y la línea dorada en T es cuánta memoria pierdes por usar una cadena en vez de acceso directo.
Mensaje. El Transformer no mejora la RNN: la sustituye. Cambia «arrastrar un estado T pasos» por «dejar que cada token pregunte a todos los demás a la vez». El resto del día es construir esa pregunta con matrices de verdad.
Términos. ht: estado oculto de la RNN en el paso t. w: ganancia efectiva por paso (autovalor dominante × derivada de la activación). αij: peso de atención con que el token i lee al token j.
Setup. La frase de juguete es una queja de cliente de telco: «la factura llegó duplicada ayer» (T = 5 tokens), con embeddings de d = 4 dimensiones interpretables: función, entidad, acción y tiempo. Arriba: la matriz X (5×4) y las tres proyecciones WQ, WK, WV (4×3). Abajo: las matrices resultantes Q, K, V (5×3 cada una), recalculadas en vivo con cada movimiento del slider. La celda que estás tocando lleva borde dorado y la fila afectada queda resaltada.
Juega. Elige celda con los dos primeros sliders y mueve su valor con el tercero. La propagación es real: el JS multiplica X por cada W en cada movimiento. Comprueba que el cambio se queda en una fila, que es lineal, y que el mismo rasgo entra con pesos distintos en q, k y v.
Lee así. Los ejes del espacio q/k son «entidad / acción / tiempo»: una query con componente alta en entidad busca tokens cuya key tenga componente alta en entidad. Ese emparejamiento se consuma en la slide siguiente con el producto QK⊤.
Mensaje. En un LLM real d = 12 288 y las W tienen millones de entradas aprendidas, pero la operación es exactamente esta: tres proyecciones lineales del mismo embedding, token a token.
Términos. X: matriz de embeddings, una fila por token. WQ, WK, WV: proyecciones aprendidas. dk: dimensión del espacio query/key (aquí 3). qi, ki, vi: filas i de Q, K, V.
Setup. Misma frase y mismas matrices de la slide anterior; ahora ejecuto los pasos 2–4 completos. Arriba: la matriz de atención A = softmax(QK⊤/√3) como heatmap 5×5 con sus valores numéricos (blanco→dorado→sepia = 0→1); la fila del token query elegido va recuadrada. Abajo: esa fila como barras sobre los tokens, y a su derecha el vector de salida zi = Σαijvj, calculado de verdad con esos pesos.
Juega. Recorre los cinco tokens con el primer slider y lee cómo cambia el reparto. Después usa el segundo slider, que reutiliza la perturbación de la slide anterior: al apagar el rasgo entidad de «factura» verás scores, softmax y salida moverse juntos.
Lee así. En el heatmap, una fila concentrada = pregunta específica; una fila plana = token sin preferencias. En las barras, el número sobre cada token es αij; las tres barras profundas de la derecha son las componentes de zi en el espacio de values.
Mensaje. Para clasificar quejas de clientes (factura / técnico / comercial, la práctica del día), esta matriz es la que decide que «duplicada» se interprete junto a «factura»: la semántica composicional sale de un producto escalar y un softmax.
Términos. S: matriz de scores (afinidades crudas). A: matriz de atención (scores normalizados por filas). αij: entrada (i,j) de A. zi: nueva representación del token i, mezcla de values.
Setup. Aquí demuestro por muestreo el detalle más fácil de recitar y más difícil de explicar del paper de 2017. Para cada dimensión dk de la rejilla genero 300 pares (q, k) con componentes N(0,1) (generador mulberry32, reproducible), calculo sus productos punto y mido la varianza empírica. Después, para 150 queries con T = 8 keys cada una, calculo el softmax de los scores sin y con el divisor √dk, y promedio la entropía de los pesos resultantes.
Juega. El slider mueve el punto gordo por ambas curvas; el botón regenera todas las muestras. El lector da los cuatro números del dk elegido: varianza medida vs teórica y entropía con vs sin escalado, en % del máximo log 8.
Lee así. Panel superior en log-log: la recta de pendiente 1 es Var = dk. Panel inferior: la curva tinta (sin escalar) se despeña hacia entropía 0 al crecer dk; la dorada (escalada) es plana. Plana = la misma temperatura de softmax a cualquier dimensión.
Mensaje. El 1/√dk no es cosmética: es un control de varianza que hace al softmax independiente de la dimensión. Sin él, GPT-3 (dk = 128 por cabeza) nacería con atenciones saturadas e inentrenables.
Términos. Var(q·k): varianza del score crudo entre vectores aleatorios. H(p): entropía de Shannon de los pesos softmax, en nats. saturación: régimen con una α ≈ 1 y gradiente ≈ 0. nats: unidades de log natural (log 8 ≈ 2.08).
Setup. Misma frase, mismas matrices, y un toggle que aplica la máscara triangular antes del softmax. Arriba: el heatmap de A; las celdas tapadas se pintan apagadas y valen exactamente 0.00. Abajo: la fila del token elegido como barras, recalculada y renormalizada en vivo.
Juega. Alterna el toggle y recorre los tokens. Fíjate en que la máscara no «borra y ya»: el softmax renormaliza, de modo que el presupuesto de atención de cada token se reparte entero entre su pasado. Las dos primeras filas son las que más cambian.
Lee así. Heatmap completo = BERT, útil cuando el texto ya existe entero (clasificar quejas, NER de contratos en BBVA). Heatmap triangular = GPT, obligatorio cuando el texto se genera de izquierda a derecha (el chatbot de atención al cliente que redacta la respuesta).
Mensaje. BERT y GPT no son arquitecturas distintas: son la misma self-attention con una máscara distinta. Una línea de código separa comprender de generar.
Términos. máscara causal: Sij = −∞ para j > i. autoregresivo: genera el token t+1 condicionando solo en 1..t. bidireccional: cada token ve toda la frase. cross-attention: queries del decoder contra keys/values del encoder.
Setup. Dos cabezas sobre la misma frase, cada una con sus WQh, WKh, WVh (4×2). La cabeza 1 está diseñada para relaciones entidad–acción (¿quién hace qué?); la cabeza 2, para tiempo (¿cuándo?). El slider s interpola las matrices de la cabeza 2 desde una copia exacta de la cabeza 1 (s = 0) hasta su versión especializada (s = 1): es una caricatura honesta de lo que el entrenamiento hace gradualmente con cabezas inicializadas casi iguales. Abajo: salidas por cabeza del token elegido, concatenación y proyección final por WO, todo calculado en vivo.
Juega. Mueve s y mira la divergencia media 〈|A(1)−A(2)|〉 del lector: es la cuantificación de cuánto añade la segunda cabeza. Luego fija s = 1 y recorre tokens comparando los dos repartos.
Lee así. En los notebooks del curso harás esto mismo con un BERT real: heatmaps por cabeza donde una atiende a la concordancia sujeto–verbo en español y otra a entidades. Aquí ves el mecanismo con números que puedes seguir a mano.
Mensaje. Multi-head es paralelización barata de capacidad expresiva: H miradas simultáneas sobre la misma frase, al precio de una.
Términos. headh: atención completa con las matrices de la cabeza h. Concat: pegar las salidas de las H cabezas en un vector de dimensión d. WO: proyección de salida que mezcla cabezas. H: número de cabezas (8–96 en modelos reales).
Setup. Arriba: las ondas Pt,j para cuatro dimensiones (j = 0, 2, 6, 14 con d = 16) en función de la posición t; el slider marca una posición y el lector da su firma numérica. Abajo, el experimento fuerte: tomo la frase, aplico una permutación real π a sus filas, recalculo TODA la atención (Q, K, V, softmax, Z) sobre la frase barajada y comparo la salida de cada token con la que tenía en el orden original. Las barras muestran z de «factura» en ambos órdenes.
Juega. Primero baraja sin PE: cero exacto siempre, la atención es ciega al orden. Luego activa PE (con la fórmula sinusoidal a d = 4 sobre la frase de juguete) y baraja: la igualdad se rompe porque cada token lleva pegada su posición.
Lee así. En negocio el orden ES información: «abono tras factura» y «factura tras abono» son quejas distintas; en un histórico de demanda, ¿subió antes o después de la promo? Sin PE, todo eso desaparece.
Mensaje. La atención compra acceso directo entre tokens pagando la noción de orden, y el positional encoding la recompra sumándola al embedding. Las variantes modernas (RoPE, ALiBi) cambian la suma por rotaciones o sesgos, con mejor extrapolación a contextos largos.
Términos. P: matriz T×d de codificación posicional. Π, π: permutación de las posiciones. equivariante: barajar la entrada baraja la salida igual, sin cambiarla. RoPE / ALiBi: posicionales modernos por rotación / sesgo lineal.
Setup. Simulo una pila de L bloques de juguete en d = 8: cada subcapa es una transformación lineal aleatoria fl(x) = s·Wlx (entradas N(0, 1/d), semilla mulberry32). Comparo dos regímenes calculados de verdad capa a capa: sin residual (x ← fl(x)) y con residual (x ← x + fl(x)), ambos con LayerNorm opcional. Arriba: similitud coseno entre xl y la entrada x0 según la profundidad. Abajo: el ejemplo numérico mínimo en 4 dimensiones, barra a barra: entrada, salida de la subcapa, suma residual y LayerNorm final.
Juega. El slider s es la «fuerza» de cada subcapa; L, cuántas apilas. El botón cambia las matrices aleatorias para comprobar que el patrón no depende de la semilla.
Lee así. La curva tinta es la slide 1 otra vez (un producto de matrices olvida), pero en profundidad. La dorada es la solución arquitectónica: con x + f(x), aunque f destruya información, x sobrevive por su carril.
Mensaje. Residual y LayerNorm no son adornos: son lo que convierte «un bloque que funciona» en «96 bloques que se pueden entrenar». Sin ellos, el Transformer profundo no existiría.
Términos. residual: salida = entrada + corrección. LN: LayerNorm, estandariza las d features de cada token. pre-norm: LN antes de la subcapa (estándar moderno). similitud coseno: cos del ángulo entre xl y x0; 1 = misma dirección, 0 = información original perdida.
Setup. El bloque ya está completo (atención multi-head + residual + LN + MLP); ahora lo apilamos L veces y contamos parámetros con la fórmula real P ≈ 12Ld². Arriba: P en función de d (ambos ejes log) para tres profundidades de referencia (L = 12, 32, 96), con tu modelo como punto dorado y las líneas horizontales de GPT-2 (0.12B), Llama-7B (6.7B) y GPT-3 (175B). Abajo: el desglose de UN bloque, 4d² de atención contra 8d² de MLP, y tu total contra los tres modelos de referencia.
Juega. Reconstruye los tres modelos históricos con dos sliders y mira el lector de memoria: es la cifra que decide si el modelo corre en tu portátil, en una GPU de 80 GB o en un clúster.
Lee así. En el panel log-log las curvas son rectas de pendiente 2 (el d²) separadas por el factor L. Moverse en diagonal (más L y más d a la vez) es como se escala en la práctica.
Mensaje. De tu juguete de d = 4 a GPT-3 no cambia ni una ecuación: cambia L, d y los datos. Esa uniformidad brutal es la que hace predecible el coste (y el presupuesto: a ≈2€/h por GPU A100, entrenar sin una estimación de P es firmar un cheque en blanco).
Términos. L: número de bloques apilados. d: dimensión del modelo (anchura). V: tamaño del vocabulario. fp16: media precisión, 2 bytes por parámetro. KV-cache: memoria extra de inferencia para guardar keys y values pasados.
Setup. El mini-dashboard final compara RNN y Transformer con las fórmulas de coste reales. Arriba: tres pares de barras en escala log — pasos secuenciales (T contra 1), FLOPs por capa (8Td² contra 4Td² + 2T²d) y tiempo de pared estimado para una GPU que ejecuta ≈2·10⁹ operaciones por ciclo, con la restricción clave: la RNN gasta al menos un ciclo POR PASO, paralelice lo que paralelice. Abajo: la ley de escala loss ∝ C−0.05 en log–log con GPT-2, GPT-3 y Chinchilla situados sobre la recta.
Juega. T y d son tus dos palancas. Busca el régimen donde 2T²d adelanta a 4Td² (el lector lo separa): ocurre en T ≈ 2d, la frontera donde el contexto largo empieza a costar más que el modelo.
Lee así. Las cuatro razones del dominio, en orden: paraleliza (barras 1 y 3), no diluye dependencias largas (slide 1: distancia 1), escala con leyes de potencia (panel inferior) y transfiere: el mismo bloque sirve para texto, imagen (ViT), audio (Whisper) y proteínas (AlphaFold). Pre-entrenar una vez y afinar mil veces — tu práctica con RoBERTa en español es exactamente eso.
Mensaje. El Transformer dominó porque convirtió el progreso en ingeniería predecible: más cómputo, mejor modelo, sobre una recta. Su único talón de Aquiles es el T², y por eso existe el Día 10.
Términos. FLOPs: operaciones de coma flotante. tiempo de pared: tiempo real transcurrido, lo que pagas. C: cómputo total de entrenamiento (≈6·P·tokens). ley de escala: relación potencial empírica loss–cómputo.
En una frase. El Transformer es una sola idea (cada token pregunta a todos los demás con un producto escalar y un softmax) envuelta en la ingeniería mínima para apilarla a lo bestia (escalado √d, multi-head, residual, LayerNorm) — y esa combinación convirtió el progreso de la IA en una recta en log–log.