13. Introducción a PyTorch

13.1 Introducción

Hasta este punto del curso hemos trabajado muchos conceptos fundamentales de Deep Learning: neuronas artificiales, funciones de activación, arquitectura de redes, propagación hacia adelante, función de pérdida, descenso del gradiente y backpropagation.

Todo eso forma la base teórica que necesitamos para entender cómo aprende una red neuronal. Sin embargo, para construir modelos reales no alcanza solo con conocer la teoría: también necesitamos una herramienta práctica que nos permita programar redes, entrenarlas y evaluarlas.

Esa herramienta será PyTorch. A partir de este tema comenzamos a entrar en la biblioteca que usaremos durante el resto del curso para implementar los modelos de Deep Learning de manera concreta.

13.2 ¿Qué es PyTorch?

PyTorch es una biblioteca de programación para Python orientada a cálculo numérico, aprendizaje automático y Deep Learning.

En términos simples, PyTorch nos da herramientas para trabajar con datos numéricos de forma eficiente y para construir redes neuronales sin tener que programar desde cero todos los detalles matemáticos del entrenamiento.

Con PyTorch podemos:

  • Representar datos mediante tensores.
  • Realizar operaciones matemáticas de forma rápida.
  • Definir modelos de redes neuronales.
  • Calcular derivadas automáticamente.
  • Entrenar modelos con CPU o GPU.
  • Guardar y cargar modelos entrenados.

Por eso PyTorch se ha convertido en una de las bibliotecas más utilizadas en educación, investigación y desarrollo profesional de inteligencia artificial.

13.3 ¿Por qué se usa tanto en Deep Learning?

PyTorch es muy popular porque logra un equilibrio muy bueno entre potencia y claridad. Permite construir modelos complejos, pero al mismo tiempo su estilo de programación resulta bastante natural para quien ya conoce Python.

Entre sus ventajas principales se suelen mencionar:

  • Su sintaxis es relativamente clara y cercana al estilo habitual de Python.
  • Permite experimentar con facilidad.
  • Tiene una gran comunidad y mucha documentación.
  • Es muy usado en investigación de inteligencia artificial.
  • Ofrece buen soporte para GPU.
  • Hace más accesible el cálculo automático de gradientes.

Esto es muy valioso porque facilita pasar de la idea teórica al código real sin una barrera técnica excesiva.

13.4 Relación entre Python y PyTorch

PyTorch no reemplaza a Python, sino que funciona dentro de Python. Es decir, escribimos programas normales en Python e importamos PyTorch como una biblioteca más.

Por ejemplo, para empezar a usarla normalmente escribimos:

import torch

Desde ese momento, el programa puede acceder a clases, funciones y estructuras que ofrece PyTorch.

Esto significa que al trabajar con PyTorch seguiremos usando variables, funciones, clases, bucles, condiciones y todas las herramientas habituales del lenguaje Python.

13.5 Qué problemas resuelve PyTorch

Si quisiéramos implementar una red neuronal completamente a mano, tendríamos que encargarnos de muchas tareas difíciles y repetitivas:

  • Representar vectores, matrices y datos multidimensionales.
  • Programar multiplicaciones matriciales y otras operaciones numéricas.
  • Calcular derivadas parciales para cada parámetro.
  • Actualizar pesos y bias en cada iteración.
  • Organizar las capas del modelo.
  • Aprovechar el hardware disponible, como una GPU.

PyTorch simplifica enormemente estas tareas. En lugar de programar todo desde cero, usamos una base sólida que ya resuelve la parte técnica pesada y nos deja concentrarnos en el modelo y en los datos.

13.6 La idea central: tensores

La estructura de datos más importante en PyTorch es el tensor. Un tensor puede verse como una generalización de números, vectores y matrices.

Por ejemplo:

  • Un escalar puede verse como un tensor de dimensión cero.
  • Una lista de números puede verse como un tensor de una dimensión.
  • Una tabla de valores puede verse como un tensor de dos dimensiones.
  • Una imagen en color puede representarse con un tensor de tres dimensiones.

En PyTorch casi todo gira alrededor de los tensores. Más adelante dedicaremos temas completos a estudiarlos en profundidad, pero desde ahora conviene entender que son el “contenedor” principal de los datos con los que trabajaremos.

13.7 Un primer ejemplo simple

Un ejemplo muy básico de uso de PyTorch puede ser crear un tensor manualmente:

import torch
x = torch.tensor([1, 2, 3, 4])
print(x)

En este caso, PyTorch crea un tensor que contiene cuatro valores. Aunque parece algo pequeño, ya estamos usando la estructura fundamental sobre la cual se construyen los modelos de Deep Learning.

La salida será algo similar a una representación interna del tensor con sus datos numéricos.

13.8 PyTorch no es solo para redes neuronales

Aunque en este curso lo utilizaremos principalmente para Deep Learning, PyTorch no se limita exclusivamente a redes neuronales.

También puede usarse para:

  • Cálculo científico.
  • Optimización numérica.
  • Procesamiento de señales.
  • Investigación matemática y computacional.
  • Prototipado rápido de algoritmos basados en tensores.

Sin embargo, su mayor fama viene de su aplicación en Machine Learning y Deep Learning.

13.9 La ventaja del cálculo automático de gradientes

Uno de los puntos más poderosos de PyTorch es que puede calcular derivadas automáticamente mediante un sistema llamado autograd.

Recordemos que en entrenamiento necesitamos gradientes para saber cómo ajustar pesos y bias. Hacer esto manualmente para redes grandes sería incómodo, propenso a errores y muy poco práctico.

PyTorch puede seguir las operaciones matemáticas realizadas y luego obtener de forma automática las derivadas necesarias para el aprendizaje.

Esto es una de las razones por las cuales bibliotecas como PyTorch hacen posible entrenar modelos complejos de manera razonable.

13.10 Qué significa programar de manera imperativa

PyTorch se hizo muy conocido, entre otras cosas, por ofrecer una forma de trabajo que se siente bastante directa. Muchas operaciones se ejecutan en el momento en que las escribimos.

Esto suele describirse como un estilo de programación imperativo o dinámico. Eso significa que el código se comporta de un modo bastante natural: se ejecuta línea por línea y podemos inspeccionar valores intermedios con facilidad.

En la práctica, esto ayuda mucho al depurar, experimentar y entender qué está haciendo el modelo en cada paso.

13.11 Componentes importantes de PyTorch

PyTorch es una biblioteca amplia. No se reduce a una sola herramienta, sino que incluye varios componentes importantes. Entre los más relevantes para este curso están:

  • torch: base principal para tensores y operaciones matemáticas.
  • torch.nn: herramientas para construir redes neuronales.
  • torch.optim: algoritmos de optimización como SGD o Adam.
  • torch.utils.data: utilidades para trabajar con datasets y DataLoader.
  • torch.cuda: funciones relacionadas con el uso de GPU.

En este tema solo las presentaremos de manera general. Más adelante iremos entrando en cada una con más detalle.

13.12 El módulo torch.nn

Cuando trabajamos con redes neuronales, una parte muy importante de PyTorch es torch.nn.

Este módulo contiene clases y herramientas para definir capas, funciones de activación, funciones de pérdida y modelos completos.

Por ejemplo, muchas capas comunes ya vienen implementadas, como:

  • Capas lineales.
  • Funciones de activación como ReLU.
  • Capas convolucionales.
  • Capas recurrentes.
  • Pérdidas como MSELoss o CrossEntropyLoss.

Gracias a esto, no hace falta programar cada componente desde cero.

13.13 El módulo torch.optim

Otro módulo muy importante es torch.optim, que contiene optimizadores listos para usar.

Recordemos que después de calcular gradientes necesitamos un mecanismo para actualizar parámetros. Ese mecanismo lo lleva adelante el optimizador.

Algunos optimizadores conocidos que suelen aparecer en PyTorch son:

  • SGD (descenso del gradiente estocástico).
  • Adam.
  • RMSprop.

La idea importante aquí es que PyTorch ya incluye estas estrategias, por lo que entrenar un modelo es mucho más directo.

13.14 El módulo torch.utils.data

En Deep Learning no solo importa el modelo; también importa cómo organizamos y entregamos los datos durante el entrenamiento.

PyTorch incluye utilidades para:

  • Representar datasets.
  • Dividir datos en lotes o batches.
  • Barajar ejemplos.
  • Cargar datos de forma ordenada durante el entrenamiento.

Esto será especialmente útil cuando pasemos de ejemplos pequeños a conjuntos de datos más realistas.

13.15 CPU y GPU en PyTorch

Una de las fortalezas de PyTorch es que puede trabajar tanto en CPU como en GPU.

La CPU es suficiente para ejemplos pequeños, ejercicios didácticos y muchas pruebas iniciales. Pero cuando los modelos y los datos crecen, la GPU puede acelerar mucho el entrenamiento.

Lo importante para un estudiante es comprender que el código general suele ser muy parecido; lo que cambia es el dispositivo donde colocamos tensores y modelos.

Más adelante veremos cómo mover datos y redes a la GPU cuando sea necesario.

13.16 Cómo se ve un flujo típico de trabajo

En PyTorch, un flujo de trabajo típico de Deep Learning suele tener una secuencia parecida a esta:

  1. Cargar o preparar datos.
  2. Representarlos como tensores.
  3. Definir el modelo.
  4. Elegir una función de pérdida.
  5. Elegir un optimizador.
  6. Ejecutar el entrenamiento durante varias épocas.
  7. Evaluar el modelo.
  8. Guardar el resultado si hace falta.

Si observas con atención, este flujo coincide bastante con toda la teoría que ya estudiamos. PyTorch no cambia la lógica del aprendizaje; simplemente nos da las herramientas para implementarla.

13.17 Ejemplo conceptual de un entrenamiento

Sin entrar todavía en todos los detalles, un entrenamiento en PyTorch suele tener una estructura general como esta:

import torch
import torch.nn as nn
import torch.optim as optim

modelo = ...
criterio = ...
optimizador = ...

for epoca in range(cantidad_de_epocas):
    prediccion = modelo(entradas)
    perdida = criterio(prediccion, salidas_reales)
    optimizador.zero_grad()
    perdida.backward()
    optimizador.step()

Aunque todavía no conozcamos todos los objetos utilizados, este esquema ya nos deja ver algo muy importante: PyTorch convierte la teoría del entrenamiento en una secuencia concreta de instrucciones.

13.18 Qué significa que un modelo sea una clase

En PyTorch, con mucha frecuencia los modelos se definen como clases de Python que heredan de nn.Module.

Esto puede sonar técnico al principio, pero la idea general es bastante razonable: una red neuronal se trata como un objeto que contiene capas, parámetros y una forma específica de procesar entradas.

De esta manera, el modelo queda organizado y es más fácil reutilizarlo, entrenarlo y evaluarlo.

Más adelante construiremos modelos propios con este enfoque paso a paso.

13.19 Qué no hace PyTorch por nosotros

Aunque PyTorch facilita enormemente el trabajo, no resuelve automáticamente todos los problemas.

Por ejemplo, PyTorch no decide por sí solo:

  • Qué arquitectura conviene usar.
  • Qué datos son adecuados.
  • Qué hiperparámetros elegir.
  • Cómo evitar overfitting.
  • Cómo interpretar correctamente los resultados.

Es decir, la biblioteca nos da herramientas muy poderosas, pero sigue siendo necesario comprender los conceptos de fondo para usarla bien.

13.20 Errores comunes al comenzar con PyTorch

Cuando un estudiante empieza a trabajar con PyTorch, es habitual encontrarse con algunas dificultades iniciales. Por ejemplo:

  • No diferenciar bien una lista de Python de un tensor.
  • Confundirse con las dimensiones de los datos.
  • No entender por qué una operación requiere tensores de cierta forma.
  • Olvidar limpiar gradientes antes de una nueva iteración.
  • Mezclar tensores en CPU con tensores en GPU.

Estos errores son completamente normales. De hecho, forman parte del aprendizaje. Lo importante es que PyTorch permite inspeccionar objetos y probar operaciones de manera bastante directa, lo que ayuda mucho a corregirlos.

13.21 Relación entre PyTorch y la teoría ya estudiada

Es importante que no veas PyTorch como algo separado de la teoría. En realidad, PyTorch es una herramienta para expresar en código lo que ya venimos estudiando conceptualmente.

Por ejemplo:

  • La entrada de la red se representa con tensores.
  • Las capas aplican transformaciones matemáticas.
  • La salida del modelo produce predicciones.
  • La función de pérdida mide el error.
  • Backpropagation obtiene gradientes.
  • El optimizador actualiza los parámetros.

En otras palabras, PyTorch nos permite llevar al terreno práctico lo que ya entendimos en forma teórica.

13.22 Qué aprenderemos después de esta introducción

Este tema tiene un objetivo panorámico: presentar la biblioteca y su lógica general. A partir del siguiente tema empezaremos a profundizar paso a paso.

En particular, lo próximo será estudiar:

  • Qué son exactamente los tensores.
  • Cómo crearlos.
  • Cómo consultar su forma.
  • Cómo operar con ellos.
  • Cómo usarlos como base de los modelos.

Es decir, ahora estamos abriendo la puerta de PyTorch; enseguida comenzaremos a recorrer sus partes más importantes.

13.23 Qué debes recordar de este tema

  • PyTorch es la biblioteca que utilizaremos para implementar Deep Learning en Python.
  • Su estructura de datos central es el tensor.
  • Incluye herramientas para modelos, pérdidas, optimizadores y manejo de datos.
  • Permite calcular gradientes automáticamente.
  • Puede trabajar con CPU y GPU.
  • No reemplaza la teoría: la lleva al código.
  • En este curso usaremos PyTorch de forma progresiva, empezando por los conceptos más básicos.

13.24 Conclusión

PyTorch será la herramienta central de la parte práctica de este curso. Gracias a ella podremos construir redes neuronales, entrenarlas, medir su desempeño y experimentar con diferentes modelos sin tener que implementar desde cero todos los aspectos matemáticos y computacionales del proceso.

La clave en esta etapa no es memorizar todas las funciones de la biblioteca, sino comprender qué papel cumple PyTorch dentro del flujo general del Deep Learning. Si esa idea queda clara, el resto del aprendizaje se vuelve mucho más natural.

En el próximo tema comenzaremos con una de las piezas más importantes de todo PyTorch: los tensores.