Skip to content

Commit 42eab6a

Browse files
feat(parte-0): ampliar Setup (002-005) con Definiciones + FAQ + Errores comunes
Framework v2: ClassSpec gana 3 campos opcionales (definiciones, faq, errores_comunes); render_readme y render_notebook los insertan en la posicion didactica correcta: README: Temas → DEFINICIONES → Dataset → Ejercicios → Homework → ERRORES → FAQ → Referencias NB : ...contenido... → DEFINICIONES → ERRORES → FAQ → Referencias Piloto aplicado a: 002 Jupyter (5 def, 5 err, 5 faq) 003 Git (6 def, 7 err, 6 faq) 004 CCDS (5 def, 5 err, 5 faq) 005 VSCode (5 def, 5 err, 5 faq) Los lotes 006-046 se ampliaran en turnos siguientes.
1 parent 5a847bf commit 42eab6a

9 files changed

Lines changed: 672 additions & 3 deletions

File tree

classes/parte-0-prerrequisitos/002-jupyter-y-jupyterlab-kernels-magics-debugging-profiling/README.md

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,23 @@ Al finalizar la clase, el alumno podrá:
3131
| 6 | `%prun` y `%lprun` | Saber qué función pesa antes de optimizar. |
3232
| 7 | Registro de kernels por venv | Cada proyecto, su propio kernel — evita el bug `import` falla. |
3333

34+
## 📖 Definiciones y características
35+
36+
**Kernel**
37+
: Proceso Python (u otro lenguaje) que ejecuta el código de las celdas. Vive separado del frontend; si lo matas, pierdes el estado en memoria pero los archivos siguen intactos. Cada notebook se asocia a UN kernel, normalmente el del venv del proyecto.
38+
39+
**Frontend**
40+
: La interfaz visual (Notebook clásico, JupyterLab, VS Code, Cursor, Colab). Todas hablan el mismo protocolo con el kernel — puedes cambiar de frontend sin perder datos si guardas el `.ipynb`.
41+
42+
**Magic**
43+
: Comando especial de IPython, no de Python. Empieza con `%` (afecta una línea) o `%%` (afecta la celda entera). Ejemplos: `%timeit`, `%matplotlib inline`, `%%time`, `%debug`. No funcionan fuera de IPython/Jupyter.
44+
45+
**`%timeit` vs `%%time`**
46+
: `%timeit` corre la expresión **muchas veces**, descarta outliers y reporta el mejor → microbenchmark estadísticamente serio. `%%time` mide **una sola corrida** del bloque → bueno para operaciones largas donde repetir cuesta. Característica clave: usa `%timeit` para algo en milisegundos, `%%time` para algo en segundos.
47+
48+
**pdb / `%debug`**
49+
: Debugger interactivo de Python. `%debug` lo lanza en modo **post-mortem** después de una excepción — entras al stack en el punto del error sin re-correr nada. Comandos: `n` siguiente línea, `s` entra a función, `c` continúa, `p var` imprime, `u/d` sube/baja en stack, `q` salir.
50+
3451
## 📂 Dataset / recursos
3552

3653
No requiere dataset externo. Usamos arreglos sintéticos con `numpy.random` para benchmarks. Para el ejercicio de debug, generamos un `ValueError` intencional.
@@ -53,6 +70,38 @@ Entrega un notebook `homework.ipynb` con: (a) celda que muestra `sys.executable`
5370

5471
**Criterio de aceptación:** El notebook abre con kernel propio (no el global), las 3 mediciones corren sin errores, y la conclusión incluye un número concreto ("NumPy es ~50× más rápido para N=1M").
5572

73+
## ⚠️ Errores comunes
74+
75+
| Síntoma / mensaje | Causa y cómo arreglar |
76+
|---|---|
77+
| `ModuleNotFoundError` aunque acabo de instalar el paquete | El kernel activo NO es el venv donde corriste `pip install`. **Fix**: en una celda, `import sys; print(sys.executable)` — si no apunta a tu venv, cambia el kernel (menú Kernel → Change Kernel) o registra el venv con `python -m ipykernel install --user --name <nombre>`. |
78+
| El notebook está "congelado" / la barra dice `[*]` | Una celda quedó atrapada en bucle infinito o esperando input. **Fix**: menú Kernel → Interrupt (Esc + I dos veces). Si no responde, Restart Kernel — perderás variables en memoria pero los archivos quedan intactos. |
79+
| Cambié código de un módulo importado y el notebook ignora el cambio | Python cachea módulos importados. **Fix**: `%load_ext autoreload` + `%autoreload 2` al inicio del notebook; recarga automáticamente al ejecutar. |
80+
| `%timeit` en una celda con asignación da error "NameError" | Las variables creadas dentro de `%timeit` **no quedan** en el namespace (corre en sandbox). **Fix**: usa `%%timeit` (cell magic) si quieres preservar variables, o asigna fuera de la magic. |
81+
| Outputs gigantes hacen el .ipynb pesado y el diff de git ilegible | Cada output (imagen, tabla) queda guardado en el JSON del notebook. **Fix**: pre-commit hook con `nbstripout` (limpia outputs antes de commitear) o `Cell → All Output → Clear` antes de guardar. |
82+
83+
## ❓ Preguntas frecuentes
84+
85+
**❓ ¿Notebook clásico o JupyterLab o VS Code?**
86+
87+
Para aprender, **VS Code** (mismo backend, mejor UX: autocomplete con type hints, debug gráfico, git inline). Para reuniones colaborativas en navegador, JupyterLab. El Notebook clásico es legacy — sigue funcionando pero ya no recibe features.
88+
89+
**❓ ¿Debo crear un kernel por proyecto o usar uno global?**
90+
91+
**Uno por proyecto.** Cada proyecto tiene dependencias distintas que entran en conflicto: el kernel global tarde o temprano se rompe. Comando: `python -m ipykernel install --user --name <proyecto>`.
92+
93+
**❓ ¿Cuándo `%timeit` no es confiable?**
94+
95+
Cuando lo que mides toca disco/red/GPU — la varianza es enorme y el min no representa típico. Usa `%%time` con varios runs manuales y reporta mediana. Tampoco confiable si la primera corrida hace JIT (numba) — calienta con un run previo.
96+
97+
**`%debug` no funciona, no muestra prompt**
98+
99+
Necesita haber ocurrido una excepción **en el kernel** justo antes. Si la celda falló pero el kernel se reinició, perdiste el stack. También: en VS Code Jupyter, usa el panel de debug en su lugar (más cómodo).
100+
101+
**❓ ¿Por qué mi notebook tarda 30 segundos en abrir si pesa solo 200 KB?**
102+
103+
Probablemente trae outputs binarios grandes (imágenes inline en base64). El JSON parece chico pero al renderizar el navegador procesa MB. Limpia outputs y guarda.
104+
56105
## 🔗 Referencias
57106

58107
- VanderPlas, **cap. 1***IPython: Beyond Normal Python*.

classes/parte-0-prerrequisitos/002-jupyter-y-jupyterlab-kernels-magics-debugging-profiling/notebook.ipynb

Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -215,6 +215,75 @@
215215
"Ver `README.md` — entrega un notebook con benchmark `%timeit` comparando `sum(range(N))` vs `np.arange(N).sum()` para N=10k/100k/1M, tabla y gráfico."
216216
]
217217
},
218+
{
219+
"cell_type": "markdown",
220+
"metadata": {},
221+
"source": [
222+
"## 📖 Definiciones y características\n",
223+
"\n",
224+
"**Kernel**\n",
225+
"\n",
226+
"Proceso Python (u otro lenguaje) que ejecuta el código de las celdas. Vive separado del frontend; si lo matas, pierdes el estado en memoria pero los archivos siguen intactos. Cada notebook se asocia a UN kernel, normalmente el del venv del proyecto.\n",
227+
"\n",
228+
"**Frontend**\n",
229+
"\n",
230+
"La interfaz visual (Notebook clásico, JupyterLab, VS Code, Cursor, Colab). Todas hablan el mismo protocolo con el kernel — puedes cambiar de frontend sin perder datos si guardas el `.ipynb`.\n",
231+
"\n",
232+
"**Magic**\n",
233+
"\n",
234+
"Comando especial de IPython, no de Python. Empieza con `%` (afecta una línea) o `%%` (afecta la celda entera). Ejemplos: `%timeit`, `%matplotlib inline`, `%%time`, `%debug`. No funcionan fuera de IPython/Jupyter.\n",
235+
"\n",
236+
"**`%timeit` vs `%%time`**\n",
237+
"\n",
238+
"`%timeit` corre la expresión **muchas veces**, descarta outliers y reporta el mejor → microbenchmark estadísticamente serio. `%%time` mide **una sola corrida** del bloque → bueno para operaciones largas donde repetir cuesta. Característica clave: usa `%timeit` para algo en milisegundos, `%%time` para algo en segundos.\n",
239+
"\n",
240+
"**pdb / `%debug`**\n",
241+
"\n",
242+
"Debugger interactivo de Python. `%debug` lo lanza en modo **post-mortem** después de una excepción — entras al stack en el punto del error sin re-correr nada. Comandos: `n` siguiente línea, `s` entra a función, `c` continúa, `p var` imprime, `u/d` sube/baja en stack, `q` salir."
243+
]
244+
},
245+
{
246+
"cell_type": "markdown",
247+
"metadata": {},
248+
"source": [
249+
"## ⚠️ Errores comunes\n",
250+
"\n",
251+
"| Síntoma / mensaje | Causa y cómo arreglar |\n",
252+
"|---|---|\n",
253+
"| `ModuleNotFoundError` aunque acabo de instalar el paquete | El kernel activo NO es el venv donde corriste `pip install`. **Fix**: en una celda, `import sys; print(sys.executable)` — si no apunta a tu venv, cambia el kernel (menú Kernel → Change Kernel) o registra el venv con `python -m ipykernel install --user --name <nombre>`. |\n",
254+
"| El notebook está \"congelado\" / la barra dice `[*]` | Una celda quedó atrapada en bucle infinito o esperando input. **Fix**: menú Kernel → Interrupt (Esc + I dos veces). Si no responde, Restart Kernel — perderás variables en memoria pero los archivos quedan intactos. |\n",
255+
"| Cambié código de un módulo importado y el notebook ignora el cambio | Python cachea módulos importados. **Fix**: `%load_ext autoreload` + `%autoreload 2` al inicio del notebook; recarga automáticamente al ejecutar. |\n",
256+
"| `%timeit` en una celda con asignación da error \"NameError\" | Las variables creadas dentro de `%timeit` **no quedan** en el namespace (corre en sandbox). **Fix**: usa `%%timeit` (cell magic) si quieres preservar variables, o asigna fuera de la magic. |\n",
257+
"| Outputs gigantes hacen el .ipynb pesado y el diff de git ilegible | Cada output (imagen, tabla) queda guardado en el JSON del notebook. **Fix**: pre-commit hook con `nbstripout` (limpia outputs antes de commitear) o `Cell → All Output → Clear` antes de guardar. |"
258+
]
259+
},
260+
{
261+
"cell_type": "markdown",
262+
"metadata": {},
263+
"source": [
264+
"## ❓ Preguntas frecuentes\n",
265+
"\n",
266+
"**❓ ¿Notebook clásico o JupyterLab o VS Code?**\n",
267+
"\n",
268+
"Para aprender, **VS Code** (mismo backend, mejor UX: autocomplete con type hints, debug gráfico, git inline). Para reuniones colaborativas en navegador, JupyterLab. El Notebook clásico es legacy — sigue funcionando pero ya no recibe features.\n",
269+
"\n",
270+
"**❓ ¿Debo crear un kernel por proyecto o usar uno global?**\n",
271+
"\n",
272+
"**Uno por proyecto.** Cada proyecto tiene dependencias distintas que entran en conflicto: el kernel global tarde o temprano se rompe. Comando: `python -m ipykernel install --user --name <proyecto>`.\n",
273+
"\n",
274+
"**❓ ¿Cuándo `%timeit` no es confiable?**\n",
275+
"\n",
276+
"Cuando lo que mides toca disco/red/GPU — la varianza es enorme y el min no representa típico. Usa `%%time` con varios runs manuales y reporta mediana. Tampoco confiable si la primera corrida hace JIT (numba) — calienta con un run previo.\n",
277+
"\n",
278+
"**❓ `%debug` no funciona, no muestra prompt**\n",
279+
"\n",
280+
"Necesita haber ocurrido una excepción **en el kernel** justo antes. Si la celda falló pero el kernel se reinició, perdiste el stack. También: en VS Code Jupyter, usa el panel de debug en su lugar (más cómodo).\n",
281+
"\n",
282+
"**❓ ¿Por qué mi notebook tarda 30 segundos en abrir si pesa solo 200 KB?**\n",
283+
"\n",
284+
"Probablemente trae outputs binarios grandes (imágenes inline en base64). El JSON parece chico pero al renderizar el navegador procesa MB. Limpia outputs y guarda."
285+
]
286+
},
218287
{
219288
"cell_type": "markdown",
220289
"metadata": {},

classes/parte-0-prerrequisitos/003-git-y-github-para-data-scientists/README.md

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,26 @@ Al finalizar la clase, el alumno podrá:
3131
| 6 | Pull Requests + review en GitHub | El review es donde se transfiere conocimiento. |
3232
| 7 | `git reflog` — la red de seguridad | Aunque borres una rama, los commits viven 90 días. |
3333

34+
## 📖 Definiciones y características
35+
36+
**Repositorio (repo)**
37+
: Carpeta con un subdirectorio `.git/` que guarda toda la historia. Características: contenido inmutable identificado por SHA-1, ramas son punteros móviles, todo cambio publicado es eterno (aunque borres el commit, vive en reflog 90 días).
38+
39+
**Commit**
40+
: Snapshot inmutable del estado del repo en un momento. Tiene SHA-1, padre(s), autor, fecha, mensaje. Característica: **atómico** — debería poder revertirse solo sin romper nada.
41+
42+
**Branch (rama)**
43+
: Puntero móvil a un commit. Mover el puntero es barato. `HEAD` apunta a la rama actual. La rama `main` no es especial; solo es la rama por defecto del proyecto.
44+
45+
**Working tree / Staging / Repo / Remote**
46+
: Las 4 zonas: working tree (lo que editas) → staging area (lo preparado con `git add`) → repo local (lo commiteado) → remote (GitHub/GitLab). Cada `git` mueve cosas entre estas 4 zonas.
47+
48+
**Merge vs Rebase**
49+
: **Merge** crea un commit nuevo que junta dos historias (preserva ambas). **Rebase** reescribe los commits de tu rama encima de otra (historia lineal pero modificada). Característica clave: **nunca rebases ramas compartidas** — reescribir SHAs rompe a tus compañeros.
50+
51+
**Conventional Commits**
52+
: Convención que prescribe `tipo(scope): descripción`. Tipos: `feat`, `fix`, `docs`, `refactor`, `test`, `chore`, `perf`, `style`. Beneficio: changelogs y semver automáticos.
53+
3454
## 📂 Dataset / recursos
3555

3656
No requiere dataset. El "dataset" son los propios cambios que el alumno hace en archivos de prueba. Para el ejercicio del `.gitignore`, simulamos archivos típicos de DS (csv pesado, `.env`, `.ipynb_checkpoints/`).
@@ -53,6 +73,44 @@ Repo público en GitHub con: 5+ commits en formato convencional, al menos 1 bran
5373

5474
**Criterio de aceptación:** El historial (`git log --oneline`) se lee como cambios atómicos coherentes. `git status` limpio después de un experimento. PR mergeado con descripción legible.
5575

76+
## ⚠️ Errores comunes
77+
78+
| Síntoma / mensaje | Causa y cómo arreglar |
79+
|---|---|
80+
| `error: failed to push some refs to 'origin/main'` | El remote tiene commits que no tienes localmente (alguien más empujó). **Fix**: `git pull --rebase` primero, resuelve conflictos si los hay, luego `git push`. |
81+
| `fatal: refusing to merge unrelated histories` | Estás juntando dos repos sin ancestro común. **Fix**: `git pull --allow-unrelated-histories` (raro, asegúrate de que es lo que querías). |
82+
| Hice `git reset --hard` y perdí mi trabajo 😱 | Si fue local y no había commit: perdido. Si había commit, **`git reflog`** lo recupera: busca el SHA antes del reset y `git reset --hard <sha>`. |
83+
| `Please tell me who you are` al hacer commit | Falta config global. **Fix**: `git config --global user.name "Tu Nombre"` y `git config --global user.email "tu@email.com"`. |
84+
| Commit con archivo enorme; ahora `git push` rechaza por >100 MB | GitHub bloquea blobs >100 MB. **Fix**: NO basta con borrar el archivo en un commit nuevo (queda en historia). Usa `git filter-repo` o BFG para reescribir historia, o agrega a `.gitignore` desde el inicio. |
85+
| Mergeé un PR pero ahora hay conflictos en `main` | Alguien mergeó algo antes y tu base local es vieja. **Fix**: `git switch main && git pull` y resuelve los conflictos en una nueva rama, no directo en main. |
86+
| `.gitignore` no funciona — el archivo sigue apareciendo en `git status` | Si el archivo **ya estaba trackeado** antes del `.gitignore`, git lo sigue viendo. **Fix**: `git rm --cached <archivo>` y commitea — desde ahora lo ignora. |
87+
88+
## ❓ Preguntas frecuentes
89+
90+
**❓ ¿Merge o rebase?**
91+
92+
Regla simple: **merge para todo lo público, rebase solo localmente antes de PR** para limpiar tus propios commits. Nunca rebases una rama que alguien más usa.
93+
94+
**❓ ¿Force push (`git push -f`) es siempre malo?**
95+
96+
En `main` o ramas compartidas: catástrofe. En tu propia rama de feature después de rebase: aceptable. Mejor usar `--force-with-lease` que falla si alguien más empujó mientras.
97+
98+
**❓ ¿Cómo deshago el último commit?**
99+
100+
Si NO empujaste: `git reset --soft HEAD~1` (mantiene cambios staged) o `--hard` (los borra). Si YA empujaste y quieres revertirlo sin reescribir historia: `git revert HEAD` (crea commit nuevo que deshace).
101+
102+
**❓ ¿Squash o no squash al mergear?**
103+
104+
Squash = un solo commit final con todo el PR. Bueno para mantener historia limpia en main. Pierdes el detalle de pasos intermedios. Política común: squash en PRs pequeños, merge commit en grandes.
105+
106+
**❓ ¿Está bien commitear el `.venv/` o el `data/raw/customers.csv`?**
107+
108+
NO. `.venv/` se reconstruye con `requirements.txt`. Datos grandes/sensibles van fuera del repo (DVC, S3, etc.) — ver clase 159 Parte 4.
109+
110+
**❓ Tengo 30 commits "wip" en mi rama, ¿qué hago antes del PR?**
111+
112+
`git rebase -i main` para entrar al rebase interactivo. Cambia `pick` por `squash` (o `fixup`) en los commits intermedios; quedará un historial limpio.
113+
56114
## 🔗 Referencias
57115

58116
- [Pro Git book](https://git-scm.com/book) — cap. 2 *Git Basics*, cap. 3 *Branching*.

0 commit comments

Comments
 (0)