The aim of the Lab is to learn to determine market parameters from the prices of traded options.
If we make assumptions about the market behavior or about the methods of option pricing, we get functions that for a given set of market (or option pricing) parameters give theoretical values of every concrete option. Black-Scholes formulas are examples of such functions that for given value of the volatility $\sigma$ and for given put or call option parameters (exercise price, duration) give the price of the option. Whenever we have such functions (which can be explicit formulas or some computer programs that compute the prices) and there are available prices of some traded options we can try to determine the unknown parameters from the known option prices. More precisely, suppose that we know the current prices $V_1,V_2,\ldots,V_m$ of $m$ different options and that $f_i(\theta)$ are the functions that give the option prices for the (unknown) market parameters $\theta$. Then we have $m$ equations: $$f_i(\theta)=V_i,\ i=1,\ldots,m.$$ Usually the number of unknown market parameters is much smaller than the number of available option prices, so the system of equations may be solved in the least squares sense by minimizing the function $$F(\theta)=\frac{1}{2}\sum_{i=1}^m (f_i(\theta)-V_i)^2.$$ Let us use the historic information about ask prices of 4.4-months call options (expiration on July 17, 2020) for AstraZeneca Plc stock available from Moodle (the data was downloaded from http://finance.yahoo.com on March 9, 2020).
(Implied volatility) Let us assume that the Black-Scholes market model with constant volatility holds, then call option prices can be computed by Black-Scholes formula. Assume $r=0.01$ and $D=0$, then the only unknown parameter is $\sigma$. Since we have only one unknown parameter, only one equation is needed to determine the value of $\sigma$ and if the assumption about the market model is correct, then every known option price should give the same value of $\sigma$. Use the equation solver fsolve from scipy.optimize to find a value of $\sigma$ for each of 10 actual option prices. Show the dependence of found $\sigma$ values on the exercise price on a graph. In order to do this, for each value of the exercise price define a function of one argument $\sigma$ that computes the difference of the corresponding theoretical call option price and the observed price of the option and use this function as an input for the command optimize.fsolve together with a suitable initial guess for the parameter $\sigma$.
Solution Assume that the data is in the file azn_2020_calls.txt in the directory h:/compfin_labs/. We need the pairs (exercise_price,option_price) and we are using the average of ask and bid prices as current option prices. Note that the columns are separated by tabulators and that there is a header line (with column names) before the actual data.
import numpy as np
from scipy import optimize
#read in the data
E,bid,ask=??
Define variables with the current market data:
T=?? #simple computation
r=??
D=??
S0=??
We need the function that computes Call option prices according to Black-Scholes formula. You can use the file ´BSformulas.py´ created during lab 2. Importing the function for the Call option can be done as follows:
import sys
sys.path.append("h:/compfin_labs") #the location of the file
import BSformulas as bs
In order to use the price for a given Call option for a given Exercises price E and exercise time T, we have only one unknown parameter $\sigma$. By the implied volatility approach, we use a known pair (exercise_price,option_price) to find such $\sigma$ that the value given by BS formula equals to the given option price. As the function fsolve in the optimize subpackage of the scipy package finds a value $x$ for which a given function $f$ is zero (solves the equation f(x)=0), we'll define a function that computes the difference of the value coming from the BS formula and the observed option price and use fsolve to find $\sigma$, for which the difference is 0.
i=0 #consider the first pair of observed exercise price and corresponding option price
def f(sigma):
???
sigma=optimize.fsolve(f,??)
print(sigma)
Do it for all pairs of (exercise price, option price) and save the results in a vector.
??
pl.plot(E,sigma_values)
pl.show()
If the BS market model with constant volatility holds, then all implied volatilities should be the same (all option prices should correspond to the same market model). As we see, the implied volatilities are not constant, but actually they change only a little. So, based on the data, we can say that the BS model with constant volatility does not hold (and thus the option prices can not be computed exactly by BS fromulas), but we may still get quit reasonable approximate prices by using the simplified market model.
Define a function that for a given value of $\sigma$ computes the sum of squares of differences of the theoretical and observed option prices and use a minimizer from scipy.optimize to find the least squares estimate of $\sigma$. For this $\sigma$, find the largest difference between the theoretical and observed option prices.
Solution
def F(sigma):
return ??
best_sigma=optimize.fmin(F,0.5)
print("The overall best sigma value:",best_sigma)
print("Maximal absolute difference:",??)
Consider Black-Scholes market model with the non-constant volatility
$$\sigma(s,t)=|\theta_0+\theta_1\frac{1}{1+0.1(s-44)^2}|.$$
From the course web page you can download a module lab5solver that contains a function lab5solver(theta,E,S0,T,r) that for a given values of $E, T, r$ and $S0$ and for a given parameter vector $\theta$ computes the theoretical price of a call option. Use the function and the option price data to find suitable values of $\theta_0$ and $\theta_1$ and find the differences between theoretical and observed option prices in the case of those parameters. NB! the function lab5solver works only if all parameters are single numbers!
Solution
Assume that the file lab5solver.py is located at the same place as the file BSformulas. Then we can import a function from the module without additional commands (showing the location of the file).
import lab5solver as l5
As this function need E to be a number (not a vector), we have to use for cycle to compute the sum of the squared differences
def F2(theta):
??
theta=optimize.fmin(F2,??)
print(theta)
Comments?
Compute the differences between theoretical and observed option prices. Compute also percentage differences. Is the model working well for the data?