Contenido del curso

- PCA Práctico: Reducción de Riesgo Financiero y Visualización

PCA Práctico: Reducción de Riesgo Financiero y Visualización

El Análisis de Componentes Principales (PCA) es una de las técnicas más poderosas para simplificar datos complejos sin perder información esencial. En el mundo financiero, donde lidiamos con decenas de variables macroeconómicas, precios de activos y métricas de riesgo, PCA nos permite identificar los factores subyacentes que realmente importan, facilitando la reducción de dimensionalidad y la visualización de patrones ocultos.

Objetivo de esta lección: Aprender a implementar PCA en Python usando scikit-learn, entender las etapas clave de preprocesamiento para datos financieros, seleccionar el número óptimo de componentes mediante scree plots y umbrales de varianza explicada, y finalmente visualizar carteras de riesgo en 2D y 3D para identificar factores de riesgo subyacentes.

1. Implementación de PCA en Python (scikit-learn)

La biblioteca scikit-learn ofrece una implementación eficiente de PCA a través de la clase PCA. El flujo básico consiste en importar la clase, ajustar el modelo a los datos estandarizados y transformar el conjunto original en nuevas componentes principales.

from sklearn.decomposition import PCA
from sklearn.preprocessing import StandardScaler
import pandas as pd
import numpy as np

# Supongamos que 'df_financiero' contiene nuestras variables (retornos, volatilidades, ratios)
scaler = StandardScaler()
datos_estandarizados = scaler.fit_transform(df_financiero)

# Aplicar PCA
pca = PCA(n_components=0.95)  # Mantener 95% de varianza explicada
componentes = pca.fit_transform(datos_estandarizados)

# Crear DataFrame con los componentes
df_pca = pd.DataFrame(componentes, columns=[f'PC{i+1}' for i in range(componentes.shape[1])])

El parámetro n_components puede ser un número entero (cantidad fija de componentes) o un valor decimal entre 0 y 1 (proporción de varianza a explicar). Para datos financieros, con frecuencia buscamos retener entre el 85% y el 95% de la varianza total.

2. Preprocesamiento: Estandarización de Datos Financieros

Los datos financieros suelen estar en escalas muy diferentes: los retornos pueden variar entre -0.1 y 0.1, las volatilidades entre 0.01 y 0.5, y los ratios (como P/E o Sharpe) pueden tener magnitudes distintas. PCA es sensible a las escalas de las variables, por lo que la estandarización es obligatoria. Sin ella, las variables con mayor magnitud dominarían injustamente las componentes principales.

  • Retornos: Suelen tener media cercana a cero, pero la varianza puede diferir entre activos.
  • Volatilidades: Generalmente expresadas como desviaciones estándar anualizadas (valores entre 0.05 y 0.6).
  • Ratios financieros: Sharpe, Sortino, Treynor; escalas típicas entre 0 y 3, pero algunas pueden ser negativas.

El proceso de estandarización transforma cada variable para que tenga media 0 y desviación estándar 1, usando StandardScaler:

from sklearn.preprocessing import StandardScaler
scaler = StandardScaler()
X_scaled = scaler.fit_transform(X)
Nota crítica: Ajusta el scaler únicamente con los datos de entrenamiento. Si luego aplicas PCA a nuevos datos, usa el mismo scaler (solo transform, no fit de nuevo) para mantener consistencia.

3. Selección del Número de Componentes (Scree Plot y Umbral de Varianza)

Seleccionar el número adecuado de componentes es un arte y una ciencia. Dos herramientas principales nos ayudan a tomar esta decisión de forma objetiva:

  • Scree Plot: Gráfico que muestra la varianza explicada por cada componente en orden descendente. Buscamos el "codo" donde la curva comienza a aplanarse, indicando que los componentes adicionales aportan poca información.
  • Umbral de varianza explicada acumulada: Definimos un valor objetivo (por ejemplo, 90% o 95%) y seleccionamos los componentes necesarios para alcanzar ese umbral.
import matplotlib.pyplot as plt

# Calcular PCA sin fijar componentes
pca_full = PCA()
pca_full.fit(X_scaled)

# Scree plot
plt.figure(figsize=(8,5))
plt.plot(range(1, len(pca_full.explained_variance_ratio_)+1), 
         pca_full.explained_variance_ratio_, 'o-', linewidth=2, color='#4a6fa5')
plt.xlabel('Componente Principal', fontsize=12)
plt.ylabel('Varianza Explicada', fontsize=12)
plt.title('Scree Plot PCA - Datos Financieros', fontsize=14)
plt.grid(True, alpha=0.3)
plt.show()

# Varianza acumulada
varianza_acumulada = np.cumsum(pca_full.explained_variance_ratio_)
print(f'Varianza explicada con 2 componentes: {varianza_acumulada[1]:.3f}')
print(f'Varianza explicada con 3 componentes: {varianza_acumulada[2]:.3f}')

En el contexto financiero, 2 o 3 componentes suelen explicar entre el 70% y el 85% de la varianza total cuando trabajamos con métricas de riesgo de distintos activos. Esto es suficiente para identificar los factores de riesgo sistémico subyacentes.

4. Caso de Uso: Reducción de Decenas de Variables Financieras a 2-3 Componentes

Imaginemos que gestionamos un fondo con 30 activos financieros. Cada activo tiene 5 métricas de riesgo: retorno esperado, volatilidad, ratio Sharpe, beta y VaR (Value at Risk). Esto nos da 150 variables en total. Con PCA, podemos reducirlas a solo 2 o 3 componentes que capturen los factores de riesgo fundamentales.

Variable original Descripción Rango típico
Retorno EsperadoRendimiento promedio anualizado-0.05 a 0.15
VolatilidadDesviación estándar anualizada0.08 a 0.40
Ratio SharpeRetorno ajustado por riesgo-0.5 a 2.0
BetaRiesgo sistemático respecto al mercado0.5 a 1.8
VaR (95%)Pérdida máxima esperada en un día-0.02 a -0.06

Después de estandarizar y aplicar PCA, las componentes resultantes pueden interpretarse como:

  • PC1 (Riesgo de Mercado Global): Correlacionada positivamente con volatilidad y beta de todos los activos. Representa el riesgo sistémico.
  • PC2 (Rendimiento Ajustado por Riesgo): Cargada positivamente con ratios Sharpe y retornos, negativamente con VaR. Refleja la eficiencia de la cartera.
  • PC3 (Riesgo Idiosincrático): Asociada a patrones específicos de sectores industriales, útil para diversificación.

5. Visualización en 2D/3D con Colores por Sectores Industriales

Una vez reducidos los datos a 2 o 3 componentes, podemos visualizarlos de forma intuitiva. Asignar colores por sector industrial (Tecnología, Salud, Finanzas, etc.) revela agrupaciones naturales y ayuda a identificar factores de riesgo comunes.

import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import Axes3D

# Ejemplo con 2 componentes
plt.figure(figsize=(10,7))
scatter = plt.scatter(df_pca['PC1'], df_pca['PC2'], 
                      c=df_financiero['sector'].astype('category').cat.codes, 
                      cmap='viridis', alpha=0.7, edgecolors='w', s=80)
plt.xlabel('Componente Principal 1 (Riesgo de Mercado)', fontsize=12)
plt.ylabel('Componente Principal 2 (Rendimiento Ajustado)', fontsize=12)
plt.title('Proyección PCA 2D - Activos Financieros por Sector', fontsize=14)
plt.colorbar(scatter, label='Sector Industrial')
plt.grid(alpha=0.3)
plt.show()

# Visualización 3D (si se usan 3 componentes)
fig = plt.figure(figsize=(12,8))
ax = fig.add_subplot(111, projection='3d')
scatter = ax.scatter(df_pca['PC1'], df_pca['PC2'], df_pca['PC3'],
                     c=df_financiero['sector'].astype('category').cat.codes,
                     cmap='plasma', alpha=0.6, s=60)
ax.set_xlabel('PC1 (Riesgo Global)')
ax.set_ylabel('PC2 (Eficiencia)')
ax.set_zlabel('PC3 (Idiosincrático)')
plt.title('PCA 3D - Factores de Riesgo por Sector Industrial', fontsize=14)
plt.colorbar(scatter, label='Sector')
plt.show()

Observamos que los activos del mismo sector tienden a agruparse en el espacio de las componentes, confirmando que PCA captura factores de riesgo compartidos. Por ejemplo, los valores de Tecnología suelen tener altas cargas en PC1 (alta volatilidad) y PC2 (alto rendimiento), mientras que los de Servicios Públicos se concentran cerca del origen en PC1 (bajo riesgo de mercado).

6. Interpretación de Componentes como Perfiles de Riesgo

La verdadera utilidad de PCA en finanzas es la capacidad de interpretar cada componente como un perfil de riesgo subyacente. Para ello, examinamos los loadings (coeficientes) de las variables originales en cada componente:

loadings = pd.DataFrame(
    pca.components_.T,
    columns=[f'PC{i+1}' for i in range(pca.n_components_)],
    index=df_financiero.columns
)
print(loadings.round(3))

Un loading alto y positivo indica que la variable contribuye fuertemente a ese componente en la misma dirección; uno alto y negativo sugiere una contribución inversa. Por ejemplo:

  • PC1 con loadings altos positivos en volatilidad y beta de todos los activos → Factor de Riesgo Sistémico de Mercado.
  • PC2 con loadings positivos en ratio Sharpe y retornos, y negativos en VaR → Factor de Calidad de la Cartera.
  • PC3 con loadings mixtos por sector → Factor de Riesgo Sectorial o Idiosincrático.
Conclusión práctica: Con solo 2-3 componentes principales hemos reducido la complejidad de decenas de variables financieras a perfiles de riesgo interpretables. Esto permite a los gestores de cartera identificar rápidamente dónde se concentra el riesgo, comparar activos en un espacio simplificado y tomar decisiones de diversificación más informadas. PCA no es solo una herramienta de reducción de dimensionalidad, sino un lente que revela la estructura oculta de los mercados financieros.

— Fin de la lección —

Implementación de PCA en Python (scikit-learn). Preprocesamiento: estandarización de datos financieros (retornos, volatilidades, ratios). Selección del número de componentes (scree plot, umbral de varianza). Caso de uso: reducción de decenas de variables financieras a 2-3 componentes para identificar factores de riesgo subyacentes. Visualización en 2D/3D con colores por sectores industriales. Interpretación de componentes como perfiles de riesgo.
Calificación
0 0

No hay comentarios por ahora.