Cómo hacer un análisis exploratorio de datos (EDA) en Python paso a paso

tutorial intermedio 26/03/2026

El análisis exploratorio de datos (EDA) es el primer paso de cualquier proyecto de Data Science. Antes de hacer modelos, predicciones o dashboards, necesitas entender tus datos: qué tienen, qué les falta, cómo se distribuyen y qué patrones esconden.

En está guía te llevo paso a paso por un EDA completo usando Python, Pandas, Matplotlib y Seaborn. Con código qué puedes copiar y adaptar a tu propio dataset.

Qué es un EDA y por qué es importante

EDA significa Exploratory Data Analysis. Es la fase en la que revisas los datos por primera vez para:

  • Entender la estructura del dataset (filas, columnas, tipos)
  • Detectar valores nulos y duplicados
  • Identificar outliers (valores atípicos)
  • Descubrir patrones y correlaciones
  • Decidir qué transformaciones necesitas antes de modelar

Sin un buen EDA, cualquier análisis posterior está construido sobre arena.

Paso 1: Cargar y explorar el dataset

import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns

# Cargar el dataset
df = pd.read_csv('datos.csv')

# Primera mirada
print(df.shape)          # (filas, columnas)
print(df.dtypes)         # tipos de cada columna
df.head(10)              # primeras 10 filas
Output de df.head() mostrando las primeras filas del DataFrame
Resultado de df.head(10) — primera vista de los datos

Con df.shape sabes cuántas filas y columnas tienes. Con df.dtypes ves si los tipos son correctos (a veces una fecha está guardada como string).

Paso 2: Resumen estadístico

# Estadísticas descriptivas
df.describe()              # numéricas
df.describe(include='O')   # categóricas

# Información general
df.info()
Output de df.describe() con estadísticas descriptivas
df.describe() — resumen estadístico de las variables numéricas

df.describe() te da media, desviación estándar, min, max y cuartiles de cada columna numérica. Es el resumen más rápido para detectar cosas raras (como un precio negativo o una edad de 999).

Paso 3: Valores nulos

# Contar nulos por columna
df.isnull().sum()

# Porcentaje de nulos
(df.isnull().mean() * 100).round(2)

# Visualizar nulos
sns.heatmap(df.isnull(), cbar=False, cmap='pink')
plt.title('Mapa de valores nulos')
plt.show()
Heatmap de valores nulos en el dataset
Mapa de calor de valores nulos — las celdas rosas indican datos faltantes

Si una columna tiene más del 40-50% de nulos, probablemente no te sirve. Si tiene pocos, puedes rellenar con la media, mediana, o eliminar las filas afectadas. Depende del contexto.

Paso 4: Duplicados

# Contar duplicados
print(f'Duplicados: {df.duplicated().sum()}')

# Ver los duplicados
df[df.duplicated(keep=False)].sort_values(by=df.columns[0])

# Eliminar duplicados
df = df.drop_duplicates()

Ojo: no todos los duplicados son errores. Dos compras identicas en el mismo día pueden ser legítimas. Siempre piensa antes de borrar.

Paso 5: Distribución de variables numéricas

# Histogramas de todas las columnas numéricas
df.hist(figsize=(12, 8), bins=30, color='#d4738a')
plt.suptitle('Distribución de variables numéricas')
plt.tight_layout()
plt.show()
Histogramas de distribución de variables numéricas
Histogramas para visualizar la distribución de cada variable
# Boxplots para detectar outliers
fig, axes = plt.subplots(1, len(df.select_dtypes('number').columns),
                          figsize=(14, 4))
for i, col in enumerate(df.select_dtypes('number').columns):
    sns.boxplot(data=df, y=col, ax=axes[i], color='#f5c6d6')
plt.tight_layout()
plt.show()
Boxplots para detección de outliers
Boxplots — los puntos fuera de los bigotes son posibles outliers

Paso 6: Variables categóricas

# Frecuencia de cada categoría
for col in df.select_dtypes(include='object').columns:
    print(f'\n--- {col} ---')
    print(df[col].value_counts().head(10))

# Gráfico de barras
fig, ax = plt.subplots(figsize=(8, 4))
df['categoría'].value_counts().head(10).plot(
    kind='barh', color='#d4738a', ax=ax)
ax.set_title('Top 10 categorías')
plt.tight_layout()
plt.show()
Gráfico de barras de las categorías más frecuentes
Top 10 categorías por frecuencia

Paso 7: Correlaciones

# Matriz de correlación
corr = df.select_dtypes('number').corr()

# Heatmap
plt.figure(figsize=(10, 8))
sns.heatmap(corr, annot=True, cmap='RdPu', center=0,
            fmt='.2f', square=True)
plt.title('Matriz de correlación')
plt.tight_layout()
plt.show()
Matriz de correlación entre variables
Heatmap de correlación — valores cercanos a 1 indican relación fuerte

Busca correlaciones fuertes (cercanas a 1 o -1). Esas son las relaciones que vale la pena investigar. Correlaciones cercanas a 0 significan que no hay relación lineal.

Paso 8: Conclusiones del EDA

Al final de un EDA, deberías poder responder:

  1. Cuántas filas y columnas tiene el dataset (y si son suficientes)
  2. Qué columnas tienen datos faltantes y cómo vas a tratarlos
  3. Si hay outliers y qué vas a hacer con ellos
  4. Que variables están correlacionadas
  5. Que transformaciones necesitas antes de modelar

Plantilla rápida para copiar

# --- EDA EXPRESS ---
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns

df = pd.read_csv('tu_archivo.csv')

# 1. Estructura
print(df.shape, '\n')
print(df.dtypes, '\n')
print(df.describe(), '\n')

# 2. Nulos y duplicados
print('Nulos:\n', df.isnull().sum(), '\n')
print('Duplicados:', df.duplicated().sum(), '\n')

# 3. Distribuciones
df.hist(figsize=(12,8), bins=30, color='#d4738a')
plt.tight_layout(); plt.show()

# 4. Correlaciones
sns.heatmap(df.select_dtypes('number').corr(),
            annot=True, cmap='RdPu', fmt='.2f')
plt.show()

Guardatelo. Yo lo uso en cada proyecto nuevo como punto de partida.

Sigue aprendiendo

← volver al blog