σμimplied vol · KKmax(S−K,0)udβρᵢⱼfat tailsPnL · drawdownyield · TdSₜ = μSₜ dt + σSₜ dWₜC = S·N(d₁) − K·e⁻ʳᵀ·N(d₂)σₚ² = wᵀΣwd₁ = [ln(S/K) + (r + σ²⁄2)T] ⁄ σ√T∂V/∂t + ½σ²S²·∂²V/∂S² + rS·∂V/∂S − rV = 0Sharpe = (Rₚ − R_f) ⁄ σₚVaR₉₉ = μ − 2.33σρ = Cov(X,Y) ⁄ σₓσᵧE[Rₚ] = Σ wᵢ·E[Rᵢ]φ(x) = e^(−x²/2) ⁄ √2πE[Rᵢ] = R_f + βᵢ(E[Rₘ] − R_f)dXₜ = θ(μ − Xₜ)dt + σ dWₜσ²ₜ = ω + α·ε²ₜ₋₁ + β·σ²ₜ₋₁C − P = S − K·e⁻ʳᵀΔ = ∂V/∂S Γ = ∂²V/∂S²p = (e^(rΔt) − d) ⁄ (u − d)rₜ = ln(Pₜ ⁄ Pₜ₋₁)E[Xₜ₊₁ | ℱₜ] = Xₜf* = (bp − q) ⁄ bz = (x − μ) ⁄ σP(N=k) = λᵏe^(−λ) ⁄ k!Θ = −∂V/∂Tν = S·φ(d₁)·√Tmin wᵀΣw s.t. wᵀμ = μ*∫Σ∂∞λ
σμimplied vol · KKmax(S−K,0)udβρᵢⱼfat tailsPnL · drawdownyield · TdSₜ = μSₜ dt + σSₜ dWₜC = S·N(d₁) − K·e⁻ʳᵀ·N(d₂)σₚ² = wᵀΣwd₁ = [ln(S/K) + (r + σ²⁄2)T] ⁄ σ√T∂V/∂t + ½σ²S²·∂²V/∂S² + rS·∂V/∂S − rV = 0Sharpe = (Rₚ − R_f) ⁄ σₚVaR₉₉ = μ − 2.33σρ = Cov(X,Y) ⁄ σₓσᵧE[Rₚ] = Σ wᵢ·E[Rᵢ]φ(x) = e^(−x²/2) ⁄ √2πE[Rᵢ] = R_f + βᵢ(E[Rₘ] − R_f)dXₜ = θ(μ − Xₜ)dt + σ dWₜσ²ₜ = ω + α·ε²ₜ₋₁ + β·σ²ₜ₋₁C − P = S − K·e⁻ʳᵀΔ = ∂V/∂S Γ = ∂²V/∂S²p = (e^(rΔt) − d) ⁄ (u − d)rₜ = ln(Pₜ ⁄ Pₜ₋₁)E[Xₜ₊₁ | ℱₜ] = Xₜf* = (bp − q) ⁄ bz = (x − μ) ⁄ σP(N=k) = λᵏe^(−λ) ⁄ k!Θ = −∂V/∂Tν = S·φ(d₁)·√Tmin wᵀΣw s.t. wᵀμ = μ*∫Σ∂∞λ
uantCraft AcademyRutas
Ctrl K
AO
+1,2 k estudiantes
Iniciar sesiónUnirse ↗
Rutas
AO
+1,2 k estudiantes
Iniciar sesión
  • English
  • Français
  • Español
  • العربية
  • Português
  • Deutsch
  • 日本語
  • 中文
Ruta de Python›Módulo 7 · Investigación de alfa y riesgo›Tema 7.5·~50 minAvanzado

VaR paramétrico

Posición en la rutaMódulo 7 de 11 · Tema 5 de 9
7.5 VaR paramétrico
—Puntuación del lab— / 100XP total—Racha—

Una fórmula en vez de un historial

El VaR histórico lee la pérdida en los rendimientos pasados. El VaR paramétrico supone que los rendimientos siguen una distribución normal y solo necesita dos números, la media y la desviación típica. La pérdida superada con probabilidad 1 - confidence es entonces z * sigma - mu, donde z es el cuantil de la normal estándar (1,645 al 95 %, 2,326 al 99 %). Es rápido, suave y se extiende fácilmente a toda una cartera, por lo que fue el estándar del sector durante décadas.

from statistics import NormalDist

def normal_var(mu, sigma, confidence):
    z = NormalDist().inv_cdf(confidence)
    return z * sigma - mu

print(round(NormalDist().inv_cdf(0.95), 4), round(NormalDist().inv_cdf(0.99), 4))
print(round(normal_var(0.0005, 0.012, 0.95), 5))        # a 95% one-day loss limit
print(round(normal_var(0.0005, 0.012, 0.99), 5))        # a higher confidence, a larger limit
# The multiplier z for common confidence levels
from statistics import NormalDist

for confidence in (0.90, 0.95, 0.975, 0.99, 0.999):
    print(confidence, round(NormalDist().inv_cdf(confidence), 3))       # 1.282, 1.645, 1.96, 2.326, 3.09

De un activo a una cartera, y a diez días

Para una cartera, la media es weights @ mu y la desviación típica sqrt(weights @ cov @ weights), las cantidades del tema de varianza de cartera. La diversificación aparece directamente: correlaciones bajas reducen la desviación y el VaR. Para un horizonte mayor, la media crece con el número de días y la desviación con su raíz cuadrada, así que un VaR a 10 días es z * sigma * sqrt(10) - mu * 10.

import numpy as np
from statistics import NormalDist

def normal_var(mu, sigma, confidence):
    return NormalDist().inv_cdf(confidence) * sigma - mu

weights = np.array([0.6, 0.4])
mu = np.array([0.0005, 0.0003])
cov = np.array([[0.00016, 0.00004], [0.00004, 0.00009]])             # volatilities 1.26% and 0.95%, correlation 0.33

mean, std = float(weights @ mu), float(np.sqrt(weights @ cov @ weights))
print(round(mean, 5), round(std, 5))
print(round(normal_var(mean, std, 0.99), 5))
print(round(normal_var(mean * 10, std * np.sqrt(10), 0.99), 5))      # the 10-day figure

Donde falla el supuesto normal

Los rendimientos reales tienen colas gruesas: los días extremos son mucho más frecuentes de lo que permite una normal. El VaR paramétrico parece entonces demasiado pequeño, sobre todo con confianza alta. Compararlo con el VaR histórico sobre los mismos datos muestra la diferencia: positiva significa que el modelo normal subestima el riesgo. Al 95 % ambos suelen ser parecidos, al 99 % pueden diferir mucho.

# Fat-tailed returns: the normal model understates the 99% loss
import numpy as np
from statistics import NormalDist

rng = np.random.default_rng(2)
returns = rng.standard_t(3, size=5000) * 0.008           # a fat-tailed distribution (3 degrees of freedom)

for confidence in (0.95, 0.99):
    historical = -np.quantile(returns, 1 - confidence)
    parametric = NormalDist().inv_cdf(confidence) * returns.std(ddof=1) - returns.mean()
    print(confidence, round(float(historical), 5), round(float(parametric), 5), round(float(historical - parametric), 5))
Elegir el método según la preguntaEl VaR paramétrico sirve para una cifra rápida y suave y para carteras de posiciones lineales. Es mala guía para opciones, cuyos rendimientos no son lineales en los factores de riesgo, y para las colas. Muchas mesas calculan varios VaR, paramétrico, histórico y Monte Carlo, y toman un gran desacuerdo como advertencia sobre el modelo.
  • VaR paramétrico = z * sigma - mu con z = NormalDist().inv_cdf(confidence): solo hacen falta la media y la desviación típica.
  • Una cartera usa weights @ mu y sqrt(weights @ cov @ weights); un horizonte multiplica la media por days y la volatilidad por sqrt(days).
  • Los rendimientos reales tienen colas gruesas: compare con el VaR histórico; una diferencia positiva significa que el modelo normal subestima el riesgo.

A continuación: el expected shortfall, la pérdida media en los días en que se supera el VaR.

Lab: qué se califica

  • Convertir dos números en un límite con normal_var25 pts
  • Cubrir toda una cartera con portfolio_normal_var25 pts
  • Mirar más lejos con horizon_var25 pts
  • Medir las colas gruesas con normality_gap25 pts
Explorador · lab-97-1
▾ lab-97-1
…
bash · en el navegador
learner@quantcraft:~/lab-97-1$
Python aún no cargadoPythonLn 1, Col 1Spaces: 4UTF-8

¿Restablecer este tema?

Todo lo que hay en lab-97-1 vuelve a los archivos iniciales y se limpia el terminal. Tu solución actual se perderá: no se puede deshacer.

Se restablecerá
  • main.py → código inicial
  • Historial del terminal y salida de pruebas
  • Cambios sin enviar
Se conservará
  • Mejor puntuación del lab
  • Tu XP y tu racha
  • Progreso de la lección y notas

Inicia sesión para ejecutar tu código.

Todas las clases se pueden leer gratis. Crea una cuenta o inicia sesión para ejecutar código, lanzar las pruebas y enviar este lab.

  • IDE en el navegador con terminal bash — sin instalar nada
  • Corrección instantánea, XP y tu lugar en la ruta
Crear una cuentaIniciar sesión
O
Continuar con GitHub