Volver al curso

Data Science con Python: Análisis de Datos para Tu Carrera

leccion
15 / 23
intermediate
8 horas
Analisis Estadistico con Python

Analisis Basico de Series Temporales

Lectura
50 min~3 min lectura

Analisis Basico de Series Temporales

Datos que Cambian en el Tiempo

Una serie temporal es una secuencia de datos ordenados cronologicamente: ventas diarias, temperaturas horarias, precios de acciones. Analizar tendencias, estacionalidad y patrones temporales es una habilidad critica para cualquier analista de datos.


Trabajar con Fechas en Pandas
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt

# Crear un rango de fechas
fechas = pd.date_range(start='2023-01-01', end='2025-12-31', freq='D')
print(f"Dias: {len(fechas)}")
print(f"Desde: {fechas[0]}")
print(f"Hasta: {fechas[-1]}")

# Generar serie temporal de ventas
np.random.seed(42)
n = len(fechas)
tendencia = np.linspace(100, 200, n)  # Tendencia creciente
estacionalidad = 30 * np.sin(2 * np.pi * np.arange(n) / 365.25)  # Ciclo anual
ruido = np.random.normal(0, 15, n)
ventas = tendencia + estacionalidad + ruido

df = pd.DataFrame({'fecha': fechas, 'ventas': ventas})
df = df.set_index('fecha')

print(df.head())
print(f"\nPeriodo: {df.index[0].strftime('%Y-%m-%d')} a {df.index[-1].strftime('%Y-%m-%d')}")

Resampling: Cambiar la Frecuencia
# De diario a semanal
df_semanal = df.resample('W').mean()
print("Ventas promedio semanal:")
print(df_semanal.head())

# De diario a mensual
df_mensual = df.resample('M').agg({
    'ventas': ['mean', 'sum', 'std', 'count']
})
df_mensual.columns = ['promedio', 'total', 'desviacion', 'dias']
print("\nResumen mensual:")
print(df_mensual.head())

# De diario a trimestral
df_trimestral = df.resample('Q').sum()
print("\nVentas trimestrales:")
print(df_trimestral.head())

Medias Moviles (Rolling)

Las medias moviles suavizan el ruido y revelan la tendencia subyacente.

# Calcular medias moviles
df['mm_7'] = df['ventas'].rolling(window=7).mean()    # 7 dias
df['mm_30'] = df['ventas'].rolling(window=30).mean()   # 30 dias
df['mm_90'] = df['ventas'].rolling(window=90).mean()   # 90 dias

# Visualizar
fig, ax = plt.subplots(figsize=(14, 6))
ax.plot(df.index, df['ventas'], alpha=0.3, label='Diario')
ax.plot(df.index, df['mm_7'], label='Media 7 dias', linewidth=1)
ax.plot(df.index, df['mm_30'], label='Media 30 dias', linewidth=2)
ax.plot(df.index, df['mm_90'], label='Media 90 dias', linewidth=2)
ax.set_title('Ventas Diarias con Medias Moviles')
ax.set_xlabel('Fecha')
ax.set_ylabel('Ventas')
ax.legend()
plt.tight_layout()
plt.show()

Analisis de Tendencia y Estacionalidad
# Comparar anios
df_pivot = df.copy()
df_pivot['anio'] = df_pivot.index.year
df_pivot['mes'] = df_pivot.index.month

ventas_por_mes = df_pivot.groupby(['anio', 'mes'])['ventas'].mean().reset_index()
ventas_pivot = ventas_por_mes.pivot(index='mes', columns='anio', values='ventas')

fig, ax = plt.subplots(figsize=(10, 6))
ventas_pivot.plot(ax=ax, marker='o')
ax.set_title('Ventas Promedio por Mes y Anio')
ax.set_xlabel('Mes')
ax.set_ylabel('Ventas promedio')
ax.set_xticks(range(1, 13))
ax.set_xticklabels(['Ene','Feb','Mar','Abr','May','Jun','Jul','Ago','Sep','Oct','Nov','Dic'])
ax.legend(title='Anio')
plt.tight_layout()
plt.show()

Crecimiento year-over-year

# Ventas mensuales totales
df_monthly = df.resample('M')['ventas'].sum()

# Cambio porcentual mes a mes
cambio_mensual = df_monthly.pct_change() * 100

# Year-over-year (comparar con mismo mes del anio anterior)
yoy = df_monthly.pct_change(periods=12) * 100

resumen = pd.DataFrame({
    'ventas': df_monthly,
    'cambio_mensual_%': cambio_mensual,
    'yoy_%': yoy
})
print("Crecimiento Year-over-Year:")
print(resumen.tail(12).round(1))

Descomposicion de Series Temporales
from statsmodels.tsa.seasonal import seasonal_decompose

# Descomponer en tendencia, estacionalidad y residuos
resultado = seasonal_decompose(df['ventas'], model='additive', period=365)

fig, axes = plt.subplots(4, 1, figsize=(14, 10))
resultado.observed.plot(ax=axes[0], title='Datos Observados')
resultado.trend.plot(ax=axes[1], title='Tendencia')
resultado.seasonal.plot(ax=axes[2], title='Estacionalidad')
resultado.resid.plot(ax=axes[3], title='Residuos')
plt.tight_layout()
plt.show()

Video Recomendado

Series Temporales con Python y Pandas


Ejercicio Practico

Crea un notebook 15_series_temporales.ipynb:

  1. Genera una serie temporal de 3 anios con tendencia creciente y estacionalidad
  2. Calcula medias moviles de 7, 30 y 90 dias
  3. Resamplea a frecuencia mensual y trimestral
  4. Calcula el crecimiento year-over-year
  5. Descompone la serie en tendencia, estacionalidad y residuos
  6. Identifica los meses de mayor y menor venta

💡 Concepto Clave

Revisemos los puntos más importantes de esta lección antes de continuar.

Resumen

  • pd.date_range(): Generar rangos de fechas
  • resample(): Cambiar frecuencia temporal (diario a mensual, etc.)
  • rolling(): Medias moviles para suavizar datos
  • pct_change(): Calcular cambios porcentuales
  • seasonal_decompose(): Separar tendencia, estacionalidad y ruido
  • Siempre visualiza tus series temporales antes de analizarlas
🧠 Pon a prueba tu conocimiento
¿Cuál es el aspecto más importante que aprendiste en esta lección?
  • Comprendo el concepto principal y puedo explicarlo con mis palabras
  • Entiendo cómo aplicarlo en mi situación específica
  • Necesito repasar algunas partes antes de continuar
  • Quiero ver más ejemplos prácticos del tema
✅ ¡Excelente! Continúa con la siguiente lección para profundizar más.