25 · pathlib: rutas del filesystem a la manera moderna
Los objetos Path superan a la concatenación de strings — une con /, inspecciona .stem / .suffix / .parent, usa glob para los shards de dataset y lee/escribe archivos en una sola llamada.
`pathlib.Path` convierte las rutas de archivo de simples strings en **objetos inteligentes** con atributos (`.name`, `.stem`, `.suffix`, `.parent`) y métodos (`.exists()`, `.glob()`, `.mkdir()`, `.read_text()`). El operador `/` une segmentos de ruta: `Path("data") / "raw" / "train.csv"` — sin más `os.path.join("data", "raw", "train.csv")`.
Sin esto:
Sin `pathlib`, unes rutas con concatenación de strings o `os.path.join`, extraes extensiones con `os.path.splitext` y compruebas existencia con `os.path.exists` — cuatro funciones distintas para lo que `Path` expone como un único objeto coherente.
Antes de pathlib, la única forma de manipular rutas de archivo en Python era como strings planos usando el módulo os.path: os.path.join("data", "raw", "train.csv"), os.path.splitext("train.csv")[0], os.path.dirname("data/raw/train.csv"). Funciona, pero dispersa la lógica en muchas llamadas a funciones y devuelve strings sin comportamiento asociado. pathlib.Path (introducido en Python 3.4, idiomático desde 3.6) te da un único objeto que sabe todo sobre sí mismo. El operador / redefine la división para realizar unión de rutas correcta según el SO — Path("data") / "raw" / "train.csv" en Windows produce data\raw\train.csv automáticamente. Los objetos Path son aceptados por open(), pandas.read_csv(), torch.load() y prácticamente cualquier función de I/O del stack científico.
Python (in browser)
`.parents` es una secuencia de todas las rutas ancestro desde el padre inmediato hasta la raíz. `.stem` elimina el sufijo final — `Path("archive.tar.gz").stem` da `"archive.tar"` (solo se elimina el último sufijo; usa `.suffixes` para todos).
Python runs entirely in your browser via Pyodide (~6 MB on first Run, cached after).
Python (in browser)
`.write_text()` y `.read_text()` son envoltorios de conveniencia sobre `open()` — gestionan apertura, escritura/lectura y cierre en una sola llamada. No reemplazan a `open()` para archivos en streaming o binarios, pero son perfectos para pequeños archivos de configuración y fragmentos de log.
Python runs entirely in your browser via Pyodide (~6 MB on first Run, cached after).
Python (in browser)
`.mkdir(parents=True, exist_ok=True)` es el idiom seguro: `parents=True` crea cada directorio ancestro faltante en la cadena (como `mkdir -p` en bash); `exist_ok=True` suprime el `FileExistsError` si el directorio ya existe. `.iterdir()` produce objetos `Path` para cada entrada del directorio — tanto archivos como subdirectorios.
Python runs entirely in your browser via Pyodide (~6 MB on first Run, cached after).
`**/*.parquet` es un glob recursivo — `**` coincide con cero o más niveles de directorio. `.glob()` es perezoso (es un generador), por lo que envolver en `sorted()` o `list()` lo materializa. En proyectos reales de ML `for p in Path("data").glob("**/*.parquet"):` es la forma canónica de enumerar datasets fragmentados.
¿Qué devuelve `Path("data/file.csv").stem`?
- `from pathlib import Path` — usa `/` para unir, `.stem` / `.suffix` / `.name` / `.parent` para inspeccionar. Reemplaza todas las funciones de string de `os.path.*`.
- `.mkdir(parents=True, exist_ok=True)` crea un árbol de directorios completo de forma segura. `.write_text()` / `.read_text()` son atajos de I/O de una línea.
- `Path("data").glob("**/*.csv")` encuentra todos los CSV de forma recursiva. Los objetos `Path` son aceptados por `open()`, pandas, torch y prácticamente cualquier función de I/O.
Todo codebase moderno de ML usa `pathlib` para directorios de ejecución: `run_dir = Path("runs") / experiment_name / run_id`. Rutas de checkpoint: `ckpt_path = run_dir / "checkpoint.pt"`. Enumerar datasets: `for csv_path in Path("data").glob("*.csv"):`. La biblioteca HuggingFace Datasets, PyTorch Lightning y MLflow aceptan objetos `Path` en sus APIs de guardar/cargar.
Si lo quitas: Sin `pathlib`, la construcción de rutas en scripts de ML degenera en concatenación frágil de strings — que falla en Windows (`\` vs `/`) y no tiene `.exists()` ni `.glob()` integrados.