La SVM cerró la lección anterior con una idea en germen: clasificar por similitud con otros puntos. K-Vecinos más cercanos (K-NN, K-Nearest Neighbors) construye un algoritmo entero sobre esa idea y nada más: para clasificar a un cliente nuevo de MercaFresh, busca los K clientes históricos más parecidos a él y vota — si la mayoría abandonó, predice churn. Sin ecuación, sin coeficientes, sin entrenamiento real. Esa simplicidad radical lo convierte en el mejor modelo para entender qué significa "parecido" en un espacio de features — y en un laboratorio perfecto para dos temas que atraviesan todo el ML: la elección de la distancia (y por qué el escalado de 03-05 vuelve a ser vital) y la maldición de la dimensionalidad.
Contenido
- Aprendizaje perezoso: un modelo que no entrena
- Métricas de distancia: euclídea y Manhattan
- El escalado vuelve a ser crítico
- La elección de K: pequeño, grande e impar
- K-NN para clasificación y para regresión
- Implementación con scikit-learn: churn de MercaFresh
- Coste en predicción y la maldición de la dimensionalidad
- K-NN es supervisado (y K-means no)
Aprendizaje perezoso: un modelo que no entrena
Todos los modelos vistos hasta ahora comprimen el dataset en unos pocos parámetros durante fit: la regresión lineal en pesos, el árbol en reglas, la SVM en vectores de soporte. K-NN no comprime nada: su fit se limita a guardar el dataset de entrenamiento (a lo sumo, indexarlo para buscar rápido). Por eso se le llama aprendizaje perezoso (lazy learning): todo el trabajo se pospone al momento de predecir.
El procedimiento de predicción, completo:
- Llega un cliente nuevo $\mathbf{x}$.
- Calcula la distancia de $\mathbf{x}$ a cada cliente del entrenamiento.
- Selecciona los K más cercanos (los "vecinos").
- Clasificación: vota la clase mayoritaria entre los vecinos (o promedia sus proporciones para dar probabilidad). Regresión: promedia sus valores.
flowchart LR
A["Cliente nuevo<br/>recencia=70, tendencia=0.5"] --> B["Distancia a los<br/>800 clientes del train"]
B --> C["K=5 vecinos<br/>mas cercanos"]
C --> D["Votacion:<br/>4 churn / 1 fiel"]
D --> E["Prediccion: CHURN<br/>p(churn) = 4/5 = 0.8"]
La hipótesis implícita es puro sentido común de negocio: clientes con features parecidas se comportan parecido. Si los cinco clientes históricamente más similares a Marta abandonaron, Marta está en riesgo. Es la misma lógica que usó KNNImputer en 03-02 para rellenar nulos con los valores de los vecinos — aquel imputador era, literalmente, un K-NN de regresión aplicado a la columna incompleta.
Métricas de distancia: euclídea y Manhattan
"Más cercano" exige definir distancia. Las dos protagonistas:
| Métrica | Fórmula (2 features) | Intuición | metric= |
|---|---|---|---|
| Euclídea | $\sqrt{(a_1-b_1)^2 + (a_2-b_2)^2}$ | Línea recta, "a vuelo de pájaro" | "euclidean" (defecto, p=2) |
| Manhattan | $|a_1-b_1| + |a_2-b_2|$ | Suma de tramos, "en cuadrícula de calles" | "manhattan" (p=1) |
Diferencia práctica: la euclídea eleva al cuadrado, así que una sola feature muy discrepante domina la distancia (como el MSE con los outliers en 04-01); la Manhattan reparte el peso linealmente y es algo más robusta a diferencias extremas en una coordenada. En datasets tabulares como el de MercaFresh, la euclídea es el punto de partida estándar; probar Manhattan es un experimento barato cuando hay features con valores extremos.
El escalado vuelve a ser crítico
Tercera aparición estelar de 03-05, y la más dramática. Calcula la distancia euclídea entre dos clientes sin escalar:
- Cliente A: recencia 30 días, ratio_inactividad 0.10
- Cliente B: recencia 90 días, ratio_inactividad 0.95
$d = \sqrt{(90-30)^2 + (0.95-0.10)^2} = \sqrt{3600 + 0.72} \approx 60.006$
El ratio_inactividad — que distingue radicalmente a ambos clientes — aporta un 0.01% de la distancia. Para K-NN sin escalar, esa feature no existe: los vecinos se eligen solo por recencia. Tras un StandardScaler o RobustScaler, ambas features hablan en unidades comparables y las dos opinan. Regla absoluta: K-NN jamás sin escalado — como la SVM (04-04), y a diferencia del árbol (04-03).
La elección de K: pequeño, grande e impar
K es el único hiperparámetro esencial, y su efecto es un pulso entre flexibilidad y estabilidad:
| K | Comportamiento | Frontera de decisión | Riesgo |
|---|---|---|---|
| 1 | Copia al vecino único más cercano | Rugosísima, islas alrededor de cada punto | Sobreajuste: el ruido manda (06-05) |
| 5–20 (típico) | Vota un vecindario razonable | Suave pero sensible a estructura local | — |
| n (todos) | Siempre predice la clase mayoritaria global | Plana: ignora las features | Underfitting total |
Visualízalo con una imagen: con K=1, cada cliente atípico del train — el fiel con perfil de churner — crea a su alrededor una pequeña isla de predicciones erróneas; un solo punto mal etiquetado contamina su vecindario. Con K=25, esa anécdota queda ahogada por la votación y la frontera se alisa; pero si K sigue creciendo, la votación incluye clientes cada vez menos parecidos y la frontera pierde el detalle real. La elección sistemática de K se hace con validación cruzada (06-03); la heurística inicial habitual es $K \approx \sqrt{n}$ y probar alrededor.
Dos consejos concretos:
- K impar en clasificación binaria: evita empates 2-2 en la votación (sklearn los resuelve, pero mejor no tenerlos).
weights="distance": da más voto a los vecinos más próximos — útil cuando K es grande y no quieres que los vecinos del borde del vecindario pesen igual que los pegados al punto.
K-NN para clasificación y para regresión
La clasificación (churn) es el caso estrella y el de nuestro ejemplo. La versión de regresión es idéntica cambiando la votación por un promedio: para estimar el gasto mensual de un cliente (el problema de 04-01), KNeighborsRegressor promedia el gasto de sus K vecinos. Produce predicciones localmente adaptativas sin asumir linealidad — pero, como el árbol de regresión (04-03), no extrapola: el gasto predicho jamás saldrá del rango de gastos de los vecinos.
Implementación con scikit-learn: churn de MercaFresh
Mismo patrón profesional que en 04-02 y 04-04: el preprocesador de 03-06 (con su escalado) y el modelo, encadenados:
from sklearn.model_selection import train_test_split
from sklearn.pipeline import Pipeline
from sklearn.neighbors import KNeighborsClassifier
# 'preprocesador': el ColumnTransformer de 03-06, con RobustScaler incluido
X_train, X_test, y_train, y_test = train_test_split(
X, y, test_size=0.2, stratify=y, random_state=42)
knn = Pipeline([
("prep", preprocesador),
("modelo", KNeighborsClassifier(n_neighbors=11, weights="distance")),
])
knn.fit(X_train, y_train) # "fit": solo preprocesar y memorizar
print(f"Accuracy en test: {knn.score(X_test, y_test):.2%}")
# La probabilidad es la proporcion (ponderada) de vecinos churn
p_churn = knn.predict_proba(X_test)[:, 1]
# Efecto de K: la curva del compromiso
for k in [1, 5, 11, 51, 201]:
m = Pipeline([("prep", preprocesador),
("modelo", KNeighborsClassifier(n_neighbors=k))])
m.fit(X_train, y_train)
print(f"K={k:3} | train: {m.score(X_train, y_train):.2%}"
f" | test: {m.score(X_test, y_test):.2%}")Lo que verás al ejecutar el bucle:
- K=1: accuracy de train = 100% siempre (el vecino más cercano de un punto del train es él mismo). Test, claramente peor: la firma del sobreajuste.
- K intermedio: el mejor test — el vecindario promedia el ruido sin diluir el patrón.
- K=201: ambas accuracies caen hacia la proporción de la clase mayoritaria — el modelo ya casi no mira al cliente.
Además, predict_proba sale gratis y con lectura directa: "8 de tus 11 vecinos abandonaron" es un argumento que el equipo de retención entiende — la interpretabilidad de K-NN no está en coeficientes ni reglas, sino en poder enseñar los vecinos que motivaron cada predicción (kneighbors() los devuelve).
Coste en predicción y la maldición de la dimensionalidad
Coste invertido. K-NN invierte el perfil de coste de todos los modelos anteriores:
| Entrenar | Predecir un punto | Memoria | |
|---|---|---|---|
| Regresión logística | Iterativo (moderado) | Instantáneo: una ecuación | Unos pesos |
| K-NN | Instantáneo: memorizar | Caro: distancias contra el train | El dataset entero |
Para un sistema en producción que puntúa cada cliente en cada visita (08-02), pagar la búsqueda de vecinos en cada predicción — y cargar con todo el histórico en memoria — puede ser prohibitivo. Los índices espaciales (algorithm="kd_tree"/"ball_tree") aceleran la búsqueda con pocas dimensiones, pero pierden eficacia al crecer estas... lo que enlaza con el problema profundo.
La maldición de la dimensionalidad. En espacios de muchas features, la geometría traiciona a la intuición: el volumen crece exponencialmente con la dimensión, los puntos se dispersan, y las distancias entre todos los pares se vuelven casi iguales — el vecino "más cercano" apenas es más cercano que el más lejano. Cuando eso pasa, "parecido" deja de significar algo y K-NN (y todo método basado en distancias, la SVM RBF incluida) degenera.
Reglas de bolsillo: con las ~15 features del dataset de churn, K-NN respira bien; con cientos de features (texto vectorizado, genómica), sufre. Las curas: la selección de features de 03-06 (menos dimensiones, más señal) y la reducción de dimensionalidad con PCA, que veremos en 05-03 precisamente como antídoto habitual antes de aplicar métodos de distancia.
K-NN es supervisado (y K-means no)
Aclaración obligada antes del módulo 5, porque la coincidencia de la letra K confunde a todo el mundo:
| K-NN (esta lección) | K-means (05-01) | |
|---|---|---|
| Tipo | Supervisado: necesita etiquetas (churn sí/no) | No supervisado: sin etiquetas |
| Qué hace | Predice la etiqueta de un punto nuevo mirando vecinos etiquetados | Descubre K grupos naturales en datos sin etiquetar |
| Qué significa K | Número de vecinos consultados | Número de grupos a formar |
K-NN responde "¿abandonará este cliente?" usando el historial etiquetado; K-means responderá "¿qué segmentos de clientes existen?" sin que nadie le diga qué buscar. Comparten la noción de distancia (y la obligación de escalar), nada más. Lo dejamos aquí: K-means tiene su lección entera al abrir el módulo 5.
Errores Comunes y Consejos
- Olvidar el escalado. En K-NN no es que el modelo rinda peor: es que las features de rango pequeño desaparecen de facto del cálculo. Siempre dentro del
Pipelinecon el preprocesador de 03-06. - Evaluar K=1 en el propio train y celebrar el 100%. Es un espejismo por construcción (cada punto es su propio vecino). Toda comparación de K debe hacerse sobre datos apartados — o mejor, con validación cruzada (06-03).
- Usar K-NN con features one-hot dominantes. Muchas columnas binarias de
ciudad_*pueden pesar tanto como todas las numéricas juntas en la distancia euclídea. Vigila la proporción de features binarias o pondera/selecciona (03-06). - Desplegarlo sin medir la latencia de predicción. Funciona de maravilla en el notebook con 800 clientes y se arrastra con 2 millones. Antes de proponerlo para producción, cronometra
predictcon el volumen real. - Consejo: usa K-NN como sonda del problema. Si con buen escalado no supera claramente a predecir la clase mayoritaria, tus features no definen una noción útil de "parecido" — y eso es un diagnóstico sobre los datos (vuelve a 03-06) que ningún modelo sofisticado va a arreglar por sí solo.
Ejercicios
Ejercicio 1. A mano: cliente nuevo con (recencia_escalada = 0.0, tendencia_escalada = 0.0). Vecinos candidatos del train: A(0.1, 0.2, fiel), B(−0.3, 0.1, fiel), C(0.8, −0.9, churn), D(0.2, −0.1, churn), E(−1.5, 1.2, fiel). Calcula las distancias euclídeas, clasifica con K=3 y con K=5, y da la probabilidad de churn en cada caso.
Ejercicio 2. Repite la clasificación K=3 del ejercicio 1 con distancia Manhattan. ¿Cambia algún vecino del top-3? ¿Cambia la predicción?
Ejercicio 3. Explica por qué KNNImputer (03-02) necesitaba que las features estuvieran en escalas comparables, usando lo aprendido en esta lección. ¿Qué feature del dataset de MercaFresh habría dominado la imputación si no se hubiera escalado?
Soluciones
Ejercicio 1
Distancias al origen: A: $\sqrt{0.01+0.04}=0.224$; B: $\sqrt{0.09+0.01}=0.316$; C: $\sqrt{0.64+0.81}=1.204$; D: $\sqrt{0.04+0.01}=0.224$; E: $\sqrt{2.25+1.44}=1.921$.
- K=3: vecinos A (fiel), D (churn), B (fiel) → votación 2-1 → fiel, p(churn) = 1/3 ≈ 0.33.
- K=5: entran también C (churn) y E (fiel) → 3 fieles, 2 churn → fiel, p(churn) = 2/5 = 0.40.
Nota cómo la probabilidad cambia con K aunque la etiqueta no: la granularidad de p es 1/K, otra razón para no usar K minúsculo si necesitas probabilidades finas.
Ejercicio 2
Manhattan: A: 0.1+0.2=0.3; B: 0.3+0.1=0.4; C: 0.8+0.9=1.7; D: 0.2+0.1=0.3; E: 1.5+1.2=2.7. El top-3 sigue siendo {A, D, B} y la predicción sigue siendo fiel (2-1). En este caso no cambia nada — las dos métricas suelen coincidir cuando los vecinos son claros; divergen sobre todo cuando algún candidato debe su cercanía euclídea a compensar una coordenada muy discrepante con otras muy parecidas (el cuadrado perdona menos que el valor absoluto).
Ejercicio 3
KNNImputer rellena el nulo de un cliente con el promedio de esa columna en sus K vecinos más cercanos — y "cercanos" se decide con distancia euclídea sobre las demás features. Es exactamente el K-NN de regresión de esta lección. Sin escalar, la feature de mayor rango numérico del dataset de MercaFresh — gasto_total (cientos o miles de euros) o en su defecto recencia_dias (hasta ~180) — habría monopolizado la distancia: los "vecinos" serían simplemente los clientes de gasto similar, ignorando tendencia, ratios y satisfacción, y las imputaciones heredarían ese sesgo. Por eso en 03-02 imputábamos dentro de un flujo que escala — y por eso el orden de las ramas del preprocesador importa.
Conclusión
K-NN te ha mostrado el ML en su expresión mínima: memorizar el pasado y predecir por semejanza. Por el camino has consolidado tres ideas transversales: la distancia es una decisión de diseño (euclídea vs. Manhattan), sin escalado no hay distancia que valga (03-05 otra vez), y K es el enésimo mando del compromiso entre memorizar y generalizar (06-05). También has visto sus facturas — predicción cara, memoria voraz, y la maldición de la dimensionalidad que motivará el PCA de 05-03 — y ha quedado clara la frontera con K-means: mismo apellido, familias distintas.
Hasta ahora, todos nuestros clasificadores deciden midiendo — distancias, márgenes, impurezas. La próxima lección recupera un camino completamente distinto que dejamos abierto en 02-05: decidir calculando probabilidades con el teorema de Bayes, como hacía nuestro detector de fraude. Convertir aquel teorema en un clasificador completo — rápido, frugal y sorprendentemente eficaz — solo requiere una suposición descaradamente falsa que funciona: la ingenuidad de Naive Bayes.
Curso de Machine Learning
Módulo 1: Introducción al Machine Learning
- ¿Qué es el Machine Learning?
- Historia y evolución del Machine Learning
- Tipos de Machine Learning
- Aplicaciones del Machine Learning
- El flujo de trabajo de un proyecto de Machine Learning
Módulo 2: Fundamentos de Estadística y Probabilidad
- Conceptos básicos de estadística
- Distribuciones de probabilidad
- Correlación y covarianza
- Inferencia estadística
- Teorema de Bayes
Módulo 3: Preprocesamiento de Datos
- Limpieza de datos
- Manejo de datos faltantes
- Transformación de datos
- Codificación de variables categóricas
- Normalización y estandarización
- Ingeniería de características
Módulo 4: Algoritmos de Machine Learning Supervisado
- Regresión lineal
- Regresión logística
- Árboles de decisión
- Máquinas de soporte vectorial (SVM)
- K-Vecinos más cercanos (K-NN)
- Naive Bayes
- Redes neuronales
Módulo 5: Algoritmos de Machine Learning No Supervisado
- Clustering: K-means
- Clustering jerárquico
- Análisis de componentes principales (PCA)
- Análisis de agrupamiento DBSCAN
- Visualización de datos con t-SNE y UMAP
Módulo 6: Evaluación y Validación de Modelos
- División de datos: entrenamiento, validación y prueba
- Métricas de evaluación
- Validación cruzada
- Curva ROC y AUC
- Overfitting y underfitting
Módulo 7: Técnicas Avanzadas y Optimización
- Regularización: Ridge, Lasso y Elastic Net
- Ensemble Learning
- Gradient Boosting
- Redes neuronales profundas (Deep Learning)
- Optimización de hiperparámetros
Módulo 8: Implementación y Despliegue de Modelos
- Frameworks y bibliotecas populares
- Implementación de modelos en producción
- Mantenimiento y monitoreo de modelos
- Consideraciones éticas y de privacidad
Módulo 9: Proyectos Prácticos
- Proyecto 1: Predicción de precios de viviendas
- Proyecto 2: Clasificación de imágenes
- Proyecto 3: Análisis de sentimientos en redes sociales
- Proyecto 4: Detección de fraudes
- Proyecto 5: Segmentación de clientes
