29 ext::shared_ptr<GeneralizedBlackScholesProcess> process1,
30 ext::shared_ptr<GeneralizedBlackScholesProcess> process2,
41 const auto callPutParityPrice = [f1, f2, df, k, optionType](
Real callPrice) ->
Real {
45 return callPrice - df*(f1-f2-k);
48 const Real vol1 = std::sqrt(variance1);
49 const Real vol2 = std::sqrt(variance2);
50 const Real sig2 = vol2*f2/(f2+k);
51 const Real sig_m = std::sqrt(variance1 +sig2*(sig2 - 2*
rho_*vol1));
53 const Real d1 = (std::log(f1) - std::log(f2 + k))/sig_m + 0.5*sig_m;
54 const Real d2 = d1 - sig_m;
58 const Real kirkCallNPV = df*(f1*N(d1) - (f2 + k)*N(d2));
60 const Real vs = vol2/(sig_m*sig_m);
64 *( -d2*rs/sig2 - 0.5*vs*sig_m * k / (f2+k)
65 *(rs*d1*d2 + (1-
rho_*
rho_)*variance1));
68 return callPutParityPrice(kirkCallNPV + 0.5*oPlt);
90 const Real R1 = f1/R2;
91 const Real vol12 = vol1*vol1;
92 const Real vol22 = vol2*vol2;
93 const Real vol23 = vol22*vol2;
96 const Real vol24 = vol22*vol22;
97 const Real vol26 = vol22*vol24;
99 const Real R22 = R2*R2;
100 const Real R24 = R22*R22;
102 const Real lnR1 = std::log(R1);
104 const Real ooPlt = -0.0625*(k2*kmR22*vol26*(-8*R22*R24*(7*k2 - 7*k*R2 + R22)*vol12*vol12
105 + kmR22*R24*vol12*(-112*k*R2 + 16*R22 + k2*(124 + 3*vol12))*vol22 - 2*kmR22*kmR22*R22*
106 (-28*k*R2 + 4*R22 + k2*(34 + 3*vol12))*vol24 + 3*k2*kmR22*kmR22*kmR22*vol26 - 4*k*(k -R2)*
107 R24*lnR1*(-4*R22*vol12 + 4*kmR22*vol22 + 3*k*(k - R2)*vol22*lnR1)))
108 /(std::exp(
squared(-(R22*vol12) + kmR22*vol22 + 2*R22*lnR1)/(8*R24*vol12 - 8*kmR22*R22*vol22))*
111 return callPutParityPrice(kirkCallNPV + 0.5*oPlt + 0.125*ooPlt);
116 const Real F22 = F2*F2;
117 const Real F23 = F22*F2;
118 const Real F24 = F22*F22;
120 const Real iR2 = 1.0/R2;
121 const Real iR22 = iR2*iR2;
122 const Real iR23 = iR22*iR2;
123 const Real iR24 = iR22*iR22;
124 const Real a = vol12 - 2*F2*iR2*
rho_*vol1*vol2 + F22*iR22*vol22;
126 const Real b = a/2+std::log(R1);
128 const Real c = std::sqrt(a);
130 const Real e =
rho_*vol1 - F2*iR2*vol2;
133 const Real g = -2*iR2*
rho_*vol1*vol2 + 2*F2*iR22*
rho_*vol1*vol2 + 2*F2*iR22*vol22 - 2*F22*iR23*vol22;
136 const Real iat = 1/c;
137 const Real l =
b*iat - c;
138 const Real m =
f*(1 - (R2*
rho_*vol1)/(F2*vol2)) - (e*iR2*k*(
d*l + (j*vol12)/(e*e))*vol2)/(2.*c);
139 const Real n = (iat*(1 - (R2*
rho_*vol1)/(F2*vol2)))/R1 - (e*iR2*k*((
f*iat)/R1 +
b/(a*R1))*vol2)/(2.*c);
140 const Real o = df*std::exp(-0.5*
f*
f);
141 const Real p =
d*l + (j*vol12)/(e*e);
142 const Real q = (-2*j*vol12*(-(iR2*vol2) + F2*iR22*vol2))/(e*e*e);
143 const Real s =
q - (b2*g)/(2.*a2) - (
b*
f*g)/(2.*a*c) + (
f*g)/(2.*c);
144 const Real u =
f*(-((
rho_*vol1)/(F2*vol2)) + (R2*
rho_*vol1)/(F22*vol2));
145 const Real v = -0.5*(
b*g*(1 - (R2*
rho_*vol1)/(F2*vol2)))/(a*c);
146 const Real w = (3*g*g)/(4.*a2*c) - (4*iR22*
rho_*vol1*vol2 - 4*F2*iR23*
rho_*vol1*vol2 +
147 2*iR22*vol22 - 8*F2*iR23*vol22 + 6*F22*iR24*vol22)/(2.*a*c);
148 const Real x = u +
v + (e*g*iR2*k*p*vol2)/(4.*a*c) + (e*iR22*k*p*vol2)/(2.*c) -
149 (e*iR2*k*
s*vol2)/(2.*c) - (iR2*k*p*vol2*(-(iR2*vol2) + F2*iR22*vol2))/(2.*c);
150 const Real y = (4*iR22 - 4*F2*iR23)*
rho_*vol1*vol2 + (2*iR22 - 8*F2*iR23 + 6*F22*iR24)*vol22;
151 const Real z = 4*iR22*
rho_*vol1*vol2 - 4*F2*iR23*
rho_*vol1*vol2 + 2*iR22*vol22 -
152 8*F2*iR23*vol22 + 6*F22*iR24*vol22;
154 const Real ooPlt = (k*o*vol23*(-2*c*b2*e2*e*(-1 +
f*
f)*F23*F24*g*g*iR22*m*vol23 +
155 2*b2*e2*e2*F23*F24*g*g*iR2*iR22*k*vol22*vol22 + 2*a*
b*e2*e*F23*F22*g*iR22*vol2*(-8*
156 e2*F2*iR2*k*vol22 + 7*
f*F22*g*m*vol22) - a*c*e2*e*F23*F22*g*iR22*vol2*(4*e*F2*
157 vol2*(-2*
b*(-1 +
f*
f)*m + e*
f*iR2*k*vol2) + F22*g*(16*m + e*(2*
f + 3*
b*iat)*iR2*k*vol2)*vol22) -
158 4*a2*a*c*e2*(e2*F22*vol2*(4*F22*iat*iR22*R2*
rho_*vol1 + 8*F23*iR22*
n*R1*vol2 -
159 4*F24*3*iR23*
n*R1*vol2 - F23*iR22*(4*iat*
rho_*vol1 + F22*iR2*k*p*vol23*w))
160 + 4*F23*F22*vol22*vol22*(iR22*(-2*F2*iR2 + 3*F22*iR22)*m + F22*(2*iR2 - 3*F2*iR22)*iR23*m
161 + F22*iR22*(-iR2 + F2*iR22)*x) + 2*e*F22*(2*F24*F2*iR24*
n*R1*vol23 +
162 2*
f*F2*F22*iR22*
rho_*vol1*vol22 - 2*
f*F22*iR22*R2*
rho_*vol1*vol22 -
163 b*F24*iR22*R2*
rho_*vol1*vol22*w - 2*F24*vol2*(iR23*
n*R1*vol22 + 4*iR23*m*vol22 - 2*iR22*vol22*x) +
164 F23*(2*iR22*m*vol23 + 6*F22*iR24*m*vol23 +
b*F22*iR22*vol23*w - 4*F22*iR23*vol23*x))) +
165 2*a2*c*e2*F23*F22*vol2*(8*F22*g*iR22*(-iR2 + F2*iR22)*m*vol23 +
166 e2*iR22*vol2*(8*F2*g*
n*R1 +
b*F22*iat*iR2*k*vol22*(
y - z)) +
167 4*e*vol22*(4*F2*g*iR22*m + F22*(-4*g*iR23*m + 2*g*iR22*x + iR22*m*z))) +
168 2*a2*a*F22*(-4*e2*e2*e*
f*F24*iat*iR24*k*vol23 + 8*e*F2*F24*iR23*(-iR22 + F2*iR23)*j*k*vol12*vol23*vol22 +
169 12*F2*F24*iR23*
squared(iR2 - F2*iR22)*j*k*vol12*vol23*vol23 +
170 e2*e2*F2*vol22*(2*F24*iR22*k*vol22*(2*(iR23*p - iR22*
s) + b2*iat*iR2*w) +
f*(4*F22*iR22*(4*m +
171 F22*iat*iR2*iR22*k*vol22) - 4*F23*(6*iR23*m + iat*iR24*k*vol22 - 2*iR22*x)
172 + F24*iR23*k*vol22*(2*
b*w + iat*
y))) - 2*e2*e*F22*iR22*(4*
f*F22*(iR2 - F2*iR22)*m*vol23 +
173 F22*vol22*(F2*vol2*(2*k*(F2*iR24*p + F2*iR24*p + iR22*
s - iR23*(2*p + F2*
s))*vol22 +
y - z)
174 + R2*
rho_*vol1*(-
y + z)))) - 2*a2*e2*F23*(2*e2*e*F23*iR22*k*(2*
b*iR22 + g*(-1 +
f*iat)*iR2)*vol23 +
175 4*
b*
f*F22*F22*g*iR22*(-iR2 + F2*iR22)*m*vol22*vol22 +
176 2*e2*F22*iR22*vol2*(2*
b*F2*iR2*(iR2 - F2*iR22)*k*vol23 + g*(2*R2*
rho_*vol1 + 2*F2*(-1 + 3*
f*m +
177 b*
f*
n*R1)*vol2 + F22*k*(-(iR22*p) + iR2*
s)*vol23)) + e*vol22*(F2*F22*g*iR22*(g*R2*
rho_*vol1 + F2*g*(-1 +
f*m)*vol2 +
178 2*F2*iR2*(-iR2 + F2*iR22)*k*p*vol23) + 2*
b*(2*F2*F22*g*iR22*
rho_*vol1 - 2*F22*g*iR22*R2*
rho_*vol1 +
179 4*
f*F23*g*iR22*m*vol2 +
f*F24*vol2*(-4*g*iR23*m + 2*g*iR22*x +
182 return callPutParityPrice(kirkCallNPV + 0.5*oPlt + 0.125*ooPlt);
Cumulative normal distribution function.
Normal distribution function.
OperatorSplittingSpreadEngine(ext::shared_ptr< GeneralizedBlackScholesProcess > process1, ext::shared_ptr< GeneralizedBlackScholesProcess > process2, Real correlation, Order order=Second)
virtual void calculate() const =0
#define QL_REQUIRE(condition, message)
throw an error if the given pre-condition is not verified
std::function< Real(Real)> b
Real DiscountFactor
discount factor between dates
functionals and combinators not included in the STL
normal, cumulative and inverse cumulative distributions
Analytic operator splitting approximation by Chi-Fai Lo (2015)
ext::shared_ptr< YieldTermStructure > q
ext::shared_ptr< BlackVolTermStructure > v