Logo
Fully annotated reference manual - version 1.8.12
Loading...
Searching...
No Matches
Functions
blacktriangulation.cpp File Reference
#include "toplevelfixture.hpp"
#include <boost/test/unit_test.hpp>
#include <ql/termstructures/volatility/equityfx/blackconstantvol.hpp>
#include <ql/time/calendars/target.hpp>
#include <ql/time/daycounters/actualactual.hpp>
#include <qle/termstructures/flatcorrelation.hpp>
#include <qle/termstructures/blacktriangulationatmvol.hpp>

Go to the source code of this file.

Functions

 BOOST_AUTO_TEST_CASE (testBlackVol)
 

Function Documentation

◆ BOOST_AUTO_TEST_CASE()

BOOST_AUTO_TEST_CASE ( testBlackVol  )

Definition at line 36 of file blacktriangulation.cpp.

36 {
37
38 BOOST_TEST_MESSAGE("Testing BlackTriangulationATMVol");
39
40 SavedSettings backup;
41
42 Date today(5, Feb, 2019);
43 Settings::instance().evaluationDate() = today;
44 Calendar cal = TARGET();
45 DayCounter dc = ActualActual(ActualActual::ISDA);
46
47 // Set up one vol and a correlation of 1.
48 // BlackTriangulationATM vol should return zero vol for every time and string
49 Handle<BlackVolTermStructure> constantVol1(QuantLib::ext::make_shared<BlackConstantVol>(today, cal, 0.1, dc));
50 Handle<CorrelationTermStructure> rhoOne(QuantLib::ext::make_shared<FlatCorrelation>(today, 1.0, dc));
51
52 BlackTriangulationATMVolTermStructure btavs(constantVol1, constantVol1, rhoOne);
53 // check it
54 for (Time t = 0.1; t < 5.0; t += 0.1) {
55 for (Real k = 100; k < 200; k += 10) {
56 Volatility v1 = btavs.blackVol(t, k);
57 BOOST_CHECK_EQUAL(v1, 0.0);
58 }
59 }
60
61 // Set up a second vol of 0.0 and a non-zero correlation, we should just get
62 // the first vol each time
63 Handle<BlackVolTermStructure> constantVol0(QuantLib::ext::make_shared<BlackConstantVol>(today, cal, 0.0, dc));
64 Handle<CorrelationTermStructure> rhoFifty(QuantLib::ext::make_shared<FlatCorrelation>(today, 0.5, dc));
65 BlackTriangulationATMVolTermStructure btavs2(constantVol1, constantVol0, rhoFifty);
66 for (Time t = 0.1; t < 5.0; t += 0.1) {
67 Real k = Null<Real>();
68 Volatility v1 = constantVol1->blackVol(t, k);
69 Volatility v2 = btavs2.blackVol(t, k);
70 BOOST_CHECK_EQUAL(v1, v2);
71 }
72
73 // Set up a second vol and a correlation of 0
74 // Triangulation vol squared should equal sum of squares
75 Handle<BlackVolTermStructure> constantVol2(QuantLib::ext::make_shared<BlackConstantVol>(today, cal, 0.2, dc));
76 Handle<CorrelationTermStructure> rhoZero(QuantLib::ext::make_shared<FlatCorrelation>(today, 0.0, dc));
77
78 BlackTriangulationATMVolTermStructure btavs3(constantVol1, constantVol2, rhoZero);
79 for (Time t = 0.1; t < 5.0; t += 0.1) {
80 Real k = Null<Real>();
81 Volatility v1 = constantVol1->blackVol(t, k);
82 Volatility v2 = constantVol2->blackVol(t, k);
83 Volatility v3 = btavs3.blackVol(t, k);
84 BOOST_CHECK_EQUAL(v1 * v1 + v2 * v2, v3 * v3);
85 }
86
87 // Now test a non-trivial case, assume correlation of 0.8 then
88 // vol between 10% and 20% should be 13.4%
89 Handle<CorrelationTermStructure> rhoEighty(QuantLib::ext::make_shared<FlatCorrelation>(today, 0.8, dc));
90 BlackTriangulationATMVolTermStructure btavs4(constantVol1, constantVol2, rhoEighty);
91 for (Time t = 0.1; t < 5.0; t += 0.1) {
92 for (Real k = 100; k < 200; k += 10) {
93 Volatility vol = btavs4.blackVol(t, k);
94 Volatility expectedVol = 0.13416407865; // calc by hand!
95 BOOST_CHECK_CLOSE(vol, expectedVol, 1E-8);
96 }
97 }
98}
Black volatility surface that implies an ATM vol based on triangulation.