Exercise · m09_delta_hedge.py
P&L of a delta-hedged option
not run yet
Not saved: sign up to keep your code"""M09 exercise 2: P&L of a delta-hedged option (notes §9.3).
Conventions: European options, no dividends, continuously compounded rate r,
time in years. The trader SELLS one option at the implied volatility sigma_i,
delta-hedges it at discrete dates, and the underlying follows GBM with drift mu
and realised volatility sigma_r. P&L is per unit option (multiply by the lot
size, e.g. 65 for Nifty, for rupees per lot).
Provided (you wrote them in M08): bs_price, bs_delta and bs_gamma from toolkit.options.
They are vectorised in S and tau; at tau = 0 the price is intrinsic value, delta the
step function (call 0/1, put -1/0) and gamma 0. Signatures:
bs_price(S, K, tau, r, sigma, kind="call"), bs_delta(...same...), bs_gamma(S, K, tau, r, sigma)
Run: cd exercises && .venv/bin/python -m pytest modules/M09-volatility-trading/tests/test_m09_delta_hedge.py
"""
from __future__ import annotations
import math
import numpy as np
from scipy.stats import norm
from toolkit.options import bs_delta, bs_gamma, bs_price # noqa: F401 (provided, M08)
# ------------------------------------------------------------------ exercises
def simulate_gbm_paths(S0, mu, sigma, T, n_steps, n_paths, seed=0):
"""Exact GBM paths S_k = S0 exp((mu - sigma^2/2) t_k + sigma W_{t_k}), t_k = k T / n_steps.
Use np.random.default_rng(seed).standard_normal((n_paths, n_steps)).
Returns an array of shape (n_paths, n_steps + 1); column 0 equals S0.
"""
raise NotImplementedError
def hedged_short_option_pnl(paths, K, T, r, sigma_i, sigma_hedge, kind="call"):
"""Terminal P&L of: sell one option at BS(sigma_i), delta-hedge with BS delta at sigma_hedge.
At t_0 the trader receives V_0 = BS(S_0, K, T, r, sigma_i), buys Delta_0 units of the
underlying (Delta computed with sigma_hedge), and holds the rest in cash at rate r.
At each t_k (k = 1..N-1) she rebalances to Delta_k = BS delta at (S_k, T - t_k,
sigma_hedge); cash grows by exp(r dt) each step. At T she pays the option payoff
and sells the hedge.
Returns an array (n_paths,) of P&L at T (NOT discounted).
Notes Prop. 9.3 and eq. (9.13).
"""
raise NotImplementedError
def gamma_theta_pnl(paths, K, T, r, sigma_i):
"""Discrete gamma-theta approximation to the LONG hedged option P&L, discounted to t=0:
sum_{k=0}^{N-1} e^{-r t_k} * 0.5 * Gamma_i(t_k, S_k) * S_k^2 * [ (dS_k / S_k)^2 - sigma_i^2 dt ]
with dS_k = S_{k+1} - S_k and Gamma_i the BS gamma at sigma_i and tau = T - t_k.
Identical for calls and puts. Notes eq. (9.12). Returns array (n_paths,).
"""
raise NotImplementedError
def expected_hedged_pnl(S0, K, T, r, mu, sigma_i, sigma_r, n_quad=2000):
"""Exact expected discounted P&L of a LONG option bought at sigma_i and continuously
hedged at sigma_i, when S is GBM(mu, sigma_r). Notes Prop. 9.4:
E[PnL] = (sigma_r^2 - sigma_i^2) * int_0^T 0.5 K e^{-rT} phi(a(t)) / sqrt(v(t)) dt,
v(t) = sigma_i^2 (T - t) + sigma_r^2 t,
a(t) = [ln(S0/K) + (mu - sigma_r^2/2) t + (r - sigma_i^2/2)(T - t)] / sqrt(v(t)).
Evaluate the integral with the midpoint rule on n_quad points. Same for calls and puts.
"""
raise NotImplementedError
No runs yet
The stub's functions raise
NotImplementedError until you write them. Fill in one, press
Run tests, and watch its tests turn green.Reference solution
Available after your first run, with an account approved for code runs.