# Accuracy of Monte-Carlo Simulation for Option Pricing

#### Joe Wong

Hi all! I have a question regarding the accuracy of Monte-Carlo simulations for option pricing. I have used the following VBA code to price a plain-vanilla European call option, and then compared the result to the output from the Black-Scholes formula. When I set the time to expiration to 3 years, the simulation result agreed with the analytical value. However, when I set the time to expiration to 8 years, the simulation result was far off from the analytical value. 100,000 iterations were used for the simulations. Could this be an issue with the random number generator provided by VBA? Please let me know if you have any insight into this issue. Thanks, Joe.

'Simulation Parameters (dt = 1/252)
nudt = (rfr - div - 0.5 * sig ^ 2) * dt
sigsdt = sig * Sqr(dt)
'Simulation begins
For i = 1 To sim

St = S0

For j = 1 To Round((T / dt), 0)
z = norm_rnd 'from box-muller
St = St * Exp(nudt + sigsdt * z)

Next j
payoff = comp_max(St - K, 0)
cum_payoff = cum_payoff + payoff * Exp(-rfr * T)

Next i
Worksheets("Sheet1").Range("B10").Value = cum_payoff / sim

#### alfredo

Sorry i'm a beginner in Vba, here is a matlab code, i think it could help you find the mistake

S0=100; K=100; r=0.06; sig=0.2; T=5; div=0;

dt = 1/252;
nudt = (r - div - 0.5 * sig ^ 2) * dt;
sigsdt = sig * sqrt(dt)
sim=10000;
Si=zeros(1,sim);

drifts=255*T
for i=1:sim
S=S0;
for j=1:drifts;
z=randn(1,1);

S = S* exp(nudt + sigsdt * z);
end
Si(i)=S;
end

payoff = max(Si - K, 0);
cal=mean(payoff) * exp(-r* T)

calbs=blsprice(S0,K,r,T,sig,div) <---B&S

results:

cal = 32.0173

calbs = 31.6150

#### Bastian Gross

##### German Mathquant
I can't find an error.

For j = 1 To Round((T / dt), 0)
might well be the source of trouble.

For j = 1 To T *252

#### Joe Wong

Alfredo,

Thanks for sharing your Matlab code with me. I think my VBA code is doing exactly the same thing. Could you try running the simulation using the following parameters and see if your simulation result agrees with the Black-Scholes formula? S0=158, K=141, r=1.30%, div=2.38%, T=8, sig=73.21%.

Thanks,
Joe

#### Joe Wong

Andy and Brastian,

Thanks for the suggestion, but I don't think rounding is the issue here as I have checked it. The difference between the round function in Excel spreadsheet and VBA is that the VBA version uses the banker's rounding (like the round function in Access) while the spreadsheet version uses our typical "normal" rounding. There is only difference (and a minor one) when the digit following the rounding digit is 5.

Regards,
Joe

results

cal =

114.5269

calbs =

91.8954

:-k

#### Andy Nguyen

I ran the matlab code and have it very close to the analytical result. Just make sure to change the simulation to 100K instead of 10K and use div in blsprice()

cal =

92.0009

calbs =

91.8954

#### Joe Wong

Thanks, Andy. If there is no error in my VBA code and the Matlab code that does essentially the same thing manage to price the call option correctly, this makes me wonder if there is something wrong with VBA random number generator, or the box-muller method in getting univariate standard normal random numbers.

#### Daniel Duffy

##### C++ author, trainer
There a lot of things that can go wrong

2. The finite difference method is bad (e.g. Euler)
3. The SDE might be 'stiff' (large e-values)
(4. Coding problem)

The books by Kloeden deal with these issues. These issues must be addressed.

Plan B: Compute the Put price (instead of Call) and then use put-call parity. Results are usually better.

#### Bastian Gross

##### German Mathquant
1. To improve your (pseudo-) random number generator use HotBits generated by radioactive decay.
2. Use refined schemes like the Milstein-method.

#### Daniel Duffy

##### C++ author, trainer
For software-based and standard RNG, the www.boost.org is a good source. In particular, Mersenne Twister.

Regarding Milstein there are several versions (explicit, implicit) and they are just OK in my experience/opinion. For special problems (e.g. Heston), some special schemes are needed in order to avoid bias.

Here is a 101 code:

#include<iostream>
#include<boost/random.hpp>
#include<boost/random/mersenne_twister.hpp>
#include<boost/random/normal_distribution.hpp>
#include<boost/random/variate_generator.hpp>
#include<ctime>
usingnamespace std;
usingnamespace boost;
int main()
{
static mt19937 rng(static_cast<unsigned> (std::time(0)));
uniform_01<mt19937> gen(rng);
return gen();
}

//

Boost C++ Libraries Installers for Windows - BoostPro Computing

#### Bastian Gross

##### German Mathquant
Predictor-corrector schemes are working well in my experience and mind.

#### Daniel Duffy

##### C++ author, trainer
Predictor-corrector schemes are working well in my experience and mind.

Are you using the Stratonovich formulation?

edit: we have tried a number of schemes for the Heston model; the Andersen QE is the best one to date.

edit2: The PC averaging in both drift and diffusion looks good. Platen and Lei Shi have a nice paper on it.

Replies
0
Views
977
Replies
0
Views
1K
Replies
3
Views
760
Replies
0
Views
781
Replies
7
Views
976