Target Encoding en Power BI: La Guía Definitiva Sin Data Leakage

Target Encoding en Power BI: La Guía Definitiva Sin Data Leakage

Domina esta técnica esencial para modelos predictivos con validación cruzada, smoothing y prevención de overfitting. Código M paso a paso + mejores prácticas.

Power BI Power Query M Language DAX ML

¿Qué es Target Encoding (Mean Encoding)?

Target Encoding es una técnica de codificación categórica que reemplaza cada categoría por el promedio de la variable objetivo para esa categoría. Es especialmente poderosa en modelos predictivos porque captura la relación real entre la categoría y el resultado.

Ejemplo Simple:

CiudadVentas
Madrid1000
Barcelona800
Madrid1200
Valencia600

Target Encoding:

CiudadTarget_Encoded
Madrid1100
Barcelona800
Valencia600
✅ Ventaja clave: Reduce dimensionalidad (1 columna vs. N en One-Hot) y mejora el rendimiento predictivo al codificar información útil.

¿Cuándo Usar Target Encoding?

📊
Alta Cardinalidad

>50 categorías únicas

🤖
ML Supervisado

Regresión o clasificación

⚙️
Feature Engineering

AutoML, XGBoost, etc.

Riesgos Críticos: Data Leakage y Overfitting

⚠️ Data Leakage: El Error Más Común Si calculas el promedio usando toda la tabla y luego entrenas el modelo, el modelo ve información del futuro. ¡Overfitting garantizado!

❌ Incorrecto (Data Leakage)

M
// ¡NO HAGAS ESTO! PromedioGlobal = Table.Group(TodaLaTabla, {"Ciudad"}, {{"Avg", each List.Average([Ventas])}})

✅ Correcto (Sin Leakage)

M
// Usa solo datos de entrenamiento PromedioTrain = Table.Group(Entrenamiento, {"Ciudad"}, {{"Avg", each List.Average([Ventas])}})

Implementación Paso a Paso en Power Query

1

Prepara tus datos

Asegúrate de tener una columna categórica (ej. Ciudad) y una variable objetivo numérica (ej. Ventas).

2

Divide en Entrenamiento y Prueba

Usa Table.AddIndexColumn + Table.SelectRows para separar datos.

M
let Fuente = TuTabla, ConIndice = Table.AddIndexColumn(Fuente, "Índice", 0, 1), TotalFilas = Table.RowCount(ConIndice), Entrenamiento = Table.SelectRows(ConIndice, each [Índice] < TotalFilas * 0.8), Prueba = Table.SelectRows(ConIndice, each [Índice] >= TotalFilas * 0.8) in [Entrenamiento, Prueba]
3

Calcula promedios en Entrenamiento

M
Promedios = Table.Group(Entrenamiento, {"Ciudad"}, { {"Target_Mean", each List.Average([Ventas]), type number}, {"Conteo", each Table.RowCount(_), Int64.Type} })
4

Une con todo el dataset

M
Resultado = Table.NestedJoin(Fuente, {"Ciudad"}, Promedios, {"Ciudad"}, "Encoding", JoinKind.LeftOuter), Expandido = Table.ExpandTableColumn(Resultado, "Encoding", {"Target_Mean", "Conteo"}, {"Target_Encoded", "Cat_Count"})

Código M Completo (Listo para Copiar)

M · Power Query
let // 1. Cargar datos Fuente = TuTablaOriginal, // 2. Agregar índice para división ConIndice = Table.AddIndexColumn(Fuente, "Índice", 0, 1, Int64.Type), TotalFilas = Table.RowCount(ConIndice), // 3. Dividir 80/20 Entrenamiento = Table.SelectRows(ConIndice, each [Índice] < TotalFilas * 0.8), Prueba = Table.SelectRows(ConIndice, each [Índice] >= TotalFilas * 0.8), // 4. Calcular Target Encoding en entrenamiento EncodingTable = Table.Group(Entrenamiento, {"Ciudad"}, { {"Target_Mean", each List.Average([Ventas]), type nullable number}, {"Cat_Count", each Table.RowCount(_), Int64.Type} }), // 5. Calcular promedio global (para smoothing) PromedioGlobal = List.Average(Entrenamiento[Ventas]), // 6. Aplicar smoothing (evita overfitting en categorías raras) MinSamples = 10, EncodingConSmoothing = Table.AddColumn(EncodingTable, "Target_Encoded", each if [Cat_Count] < MinSamples then PromedioGlobal else ([Target_Mean] * [Cat_Count] + PromedioGlobal * MinSamples) / ([Cat_Count] + MinSamples) ), // 7. Unir con dataset completo Resultado = Table.NestedJoin(ConIndice, {"Ciudad"}, EncodingConSmoothing, {"Ciudad"}, "Temp", JoinKind.LeftOuter), Expandido = Table.ExpandTableColumn(Resultado, "Temp", {"Target_Encoded"}, {"Ciudad_Target"}), // 8. Limpiar Final = Table.SelectColumns(Expandido, List.RemoveItems(Table.ColumnNames(Expandido), {"Índice", "Temp"})) in Final
✅ Smoothing incluido: Categorías con menos de 10 muestras usan promedio global. ¡Evita overfitting!

Uso en DAX: Medidas Dinámicas

DAX
Ventas_Promedio_Ciudad = CALCULATE( AVERAGE(Ventas[Ventas]), ALLEXCEPT(Ciudades, Ciudades[Ciudad]) ) // Con filtro de fecha Impacto_Temporal = CALCULATE( [Ventas_Promedio_Ciudad], DATESINPERIOD(Calendar[Date], MAX(Calendar[Date]), -30, DAY) )

Conclusión: Tu Modelo Listo para Producción

🛡️
Sin Data Leakage

Validación cruzada correcta

📉
Baja Dimensionalidad

1 columna vs. N en One-Hot

📈
Mejor Predicción

Captura relaciones reales

¡Ya dominas Target Encoding como un Data Scientist profesional! Implementa esta técnica en tus modelos de AutoML, exporta a Azure ML o intégrala en dashboards predictivos.

Entradas populares de este blog

Análisis ABC en Power BI con DAX.

Cómo Realizar One-Hot Encoding en Power BI.

Cómo Equilibrar Múltiples Productos con Pedidos a la Medida

Descubriendo el Poder de los Modelos de Clasificación en Machine Learning: Predicciones Precisas y Clasificaciones Sorprendentes

Maximiza la rentabilidad de tu negocio: Cómo optimizar la selección de proveedores de mercancías.

Optimización del Inventario Multiproducto en Espacios Reducidos: Una guía para la eficiencia en gestión de stocks

El Desafío del Empaque en Contenedores: Optimizando Espacios en contenedores con Ingenio

¡Plan Desagregado de Producción como un jefe!

Domina tu Almacén sin arruinarte: El Juego del Modelo de Inventario Múltiproductos con Presupuesto ajustado