- 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.
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)
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 Esperado | Rendimiento promedio anualizado | -0.05 a 0.15 |
| Volatilidad | Desviación estándar anualizada | 0.08 a 0.40 |
| Ratio Sharpe | Retorno ajustado por riesgo | -0.5 a 2.0 |
| Beta | Riesgo sistemático respecto al mercado | 0.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.
— Fin de la lección —
No hay comentarios por ahora.
Compartir este contenido
Compartir enlace
Compartir en redes sociales
Compartir por correo electrónico
Please iniciar sesión para compartir esto Artículo por correo electrónico.