Reprice the option at , , and . Delta is the difference between the two bumped prices divided by . Gamma is the sum of the bumped prices less twice the centre price, divided by . On a six-month call with , , , and , a -dollar bump yields delta about and gamma about .
See which Taylor terms the bumps cancel
Expanding and in Taylor series and subtracting cancels the even terms. Adding the expansions and subtracting cancels the odd terms. For a sufficiently smooth price,
Both have truncation error in this setting. For a Black–Scholes call with no dividends, and . When bumping spot, keep maturity, strike, rate and volatility fixed to measure the same model derivatives. If a hedging model specifies that implied volatility changes with spot, state and test that convention separately.
Delta divides the difference between two revaluations by , which is the distance between the bumped spots. Gamma divides the change in the two slopes by again, so its denominator is . Reprice all three points with the same strike, maturity, rate and volatility for a partial derivative with respect to spot. If you use a Monte Carlo pricer, common random numbers help remove noise that would otherwise be magnified by these divisions. Compare several bump sizes before interpreting a single error.
Change the bump and compare with the analytic Greeks
The analytic delta and gamma are and . With , prices at , , and are about , , and . With , the delta and gamma estimates are and . The smaller bump comes closer here because analytic repricing has little noise at the dollar scale. With Monte Carlo repricing, reuse the same shocks at all three spots and estimate the uncertainty of the per-path price differences.
Central differences with a bump sweep
from math import exp, log, sqrt
from scipy.stats import norm
strike, maturity, rate, vol = 105, 0.5, 0.04, 0.25
spot = 100
def call_price(s):
d1 = (log(s / strike) + (rate + vol**2 / 2) * maturity) / (vol * sqrt(maturity))
return s * norm.cdf(d1) - strike * exp(-rate * maturity) * norm.cdf(
d1 - vol * sqrt(maturity)
)
center = call_price(spot)
for h in (5, 1, 0.1, 0.01):
below, above = call_price(spot - h), call_price(spot + h)
delta = (above - below) / (2 * h)
gamma = (above - 2 * center + below) / h**2
print(h, delta, gamma)Explore the price curve in the options pricer to see where its slope and curvature are changing.