Re: OptionletStripper question
Posted by
Nathan Abbott on
May 01, 2008; 12:26am
URL: http://quantlib.414.s1.nabble.com/OptionletStripper-question-tp5928p5930.html
Sorry I have not gotten back to you earlier, because I have been sick. The short term solution I decide to use is to convert the prices into implied volatilities. Now I have this new problem. When the optionletStripper1 class is deleted after it been calculated, it takes 21 seconds to delete. Is this normal.
Here is an example I have written. It was written with Visual Studio 2005 and boost 1.34.1
#include <ql/quantlib.hpp>
#ifdef BOOST_MSVC
#endif
#include <boost/timer.hpp>
#include <iostream>
#include <iomanip>
using namespace QuantLib;
#if defined(QL_ENABLE_SESSIONS)
namespace QuantLib {
Integer sessionId() { return 0; }
}
#endif
int main(int, char* []) {
try {
boost::timer timer;
std::cout << "Test optionletstripper1 & StrippedOptionletAdapter deletion...";
Real accuracy = 1.0e-6;
Real tolerance = 1.0e-5;
// create yield curve
Calendar calendar;
DayCounter dayCounter;
RelinkableHandle<YieldTermStructure> yieldTermStructure;
calendar = TARGET();
Date today = calendar.adjust(Date::todaysDate());
Settings::instance().evaluationDate() = today;
dayCounter = Actual365Fixed();
Rate flatFwdRate = 0.04;
yieldTermStructure.linkTo(
boost::shared_ptr<FlatForward>(new FlatForward(0,
calendar,
flatFwdRate,
dayCounter)));
// create vol surface
std::vector<Rate> strikes;
std::vector<Period> optionTenors;
Matrix termV;
boost::shared_ptr<CapFloorTermVolSurface> capFloorVolSurface;
// tenors vector
optionTenors = std::vector<Period>();
optionTenors.push_back(Period(1, Years));
optionTenors.push_back(Period(18, Months));
optionTenors.push_back(Period(2, Years));
optionTenors.push_back(Period(3, Years));
optionTenors.push_back(Period(4, Years));
optionTenors.push_back(Period(5, Years));
optionTenors.push_back(Period(6, Years));
optionTenors.push_back(Period(7, Years));
optionTenors.push_back(Period(8, Years));
optionTenors.push_back(Period(9, Years));
optionTenors.push_back(Period(10, Years));
optionTenors.push_back(Period(12, Years));
optionTenors.push_back(Period(15, Years));
optionTenors.push_back(Period(20, Years));
optionTenors.push_back(Period(25, Years));
optionTenors.push_back(Period(30, Years));
// strikes vector
strikes = std::vector<Rate>();
strikes.push_back(0.015);
strikes.push_back(0.0175);
strikes.push_back(0.02);
strikes.push_back(0.0225);
strikes.push_back(0.025);
strikes.push_back(0.03);
strikes.push_back(0.035);
strikes.push_back(0.04);
strikes.push_back(0.05);
strikes.push_back(0.06);
strikes.push_back(0.07);
strikes.push_back(0.08);
strikes.push_back(0.1);
// volatilities matrix
termV = Matrix(optionTenors.size(), strikes.size());
termV[0][0]=0.287; termV[0][1]=0.274; termV[0][2]=0.256; termV[0][3]=0.245; termV[0][4]=0.227; termV[0][5]=0.148; termV[0][6]=0.096; termV[0][7]=0.09; termV[0][8]=0.11; termV[0][9]=0.139; termV[0][10]=0.166; termV[0][11]=0.19; termV[0][12]=0.214;
termV[1][0]=0.303; termV[1][1]=0.258; termV[1][2]=0.22; termV[1][3]=0.203; termV[1][4]=0.19; termV[1][5]=0.153; termV[1][6]=0.126; termV[1][7]=0.118; termV[1][8]=0.147; termV[1][9]=0.165; termV[1][10]=0.18; termV[1][11]=0.192; termV[1][12]=0.212;
termV[2][0]=0.303; termV[2][1]=0.257; termV[2][2]=0.216; termV[2][3]=0.196; termV[2][4]=0.182; termV[2][5]=0.154; termV[2][6]=0.134; termV[2][7]=0.127; termV[2][8]=0.149; termV[2][9]=0.166; termV[2][10]=0.18; termV[2][11]=0.192; termV[2][12]=0.212;
termV[3][0]=0.305; termV[3][1]=0.266; termV[3][2]=0.226; termV[3][3]=0.203; termV[3][4]=0.19; termV[3][5]=0.167; termV[3][6]=0.151; termV[3][7]=0.144; termV[3][8]=0.16; termV[3][9]=0.172; termV[3][10]=0.183; termV[3][11]=0.193; termV[3][12]=0.209;
termV[4][0]=0.294; termV[4][1]=0.261; termV[4][2]=0.216; termV[4][3]=0.201; termV[4][4]=0.19; termV[4][5]=0.171; termV[4][6]=0.158; termV[4][7]=0.151; termV[4][8]=0.163; termV[4][9]=0.172; termV[4][10]=0.181; termV[4][11]=0.188; termV[4][12]=0.201;
termV[5][0]=0.276; termV[5][1]=0.248; termV[5][2]=0.212; termV[5][3]=0.199; termV[5][4]=0.189; termV[5][5]=0.172; termV[5][6]=0.16; termV[5][7]=0.155; termV[5][8]=0.162; termV[5][9]=0.17; termV[5][10]=0.177; termV[5][11]=0.183; termV[5][12]=0.195;
termV[6][0]=0.26; termV[6][1]=0.237; termV[6][2]=0.21; termV[6][3]=0.198; termV[6][4]=0.188; termV[6][5]=0.172; termV[6][6]=0.161; termV[6][7]=0.156; termV[6][8]=0.161; termV[6][9]=0.167; termV[6][10]=0.173; termV[6][11]=0.179; termV[6][12]=0.19;
termV[7][0]=0.25; termV[7][1]=0.231; termV[7][2]=0.208; termV[7][3]=0.196; termV[7][4]=0.187; termV[7][5]=0.172; termV[7][6]=0.162; termV[7][7]=0.156; termV[7][8]=0.16; termV[7][9]=0.165; termV[7][10]=0.17; termV[7][11]=0.175; termV[7][12]=0.185;
termV[8][0]=0.244; termV[8][1]=0.226; termV[8][2]=0.206; termV[8][3]=0.195; termV[8][4]=0.186; termV[8][5]=0.171; termV[8][6]=0.161; termV[8][7]=0.156; termV[8][8]=0.158; termV[8][9]=0.162; termV[8][10]=0.166; termV[8][11]=0.171; termV[8][12]=0.18;
termV[9][0]=0.239; termV[9][1]=0.222; termV[9][2]=0.204; termV[9][3]=0.193; termV[9][4]=0.185; termV[9][5]=0.17; termV[9][6]=0.16; termV[9][7]=0.155; termV[9][8]=0.156; termV[9][9]=0.159; termV[9][10]=0.163; termV[9][11]=0.168; termV[9][12]=0.177;
termV[10][0]=0.235; termV[10][1]=0.219; termV[10][2]=0.202; termV[10][3]=0.192; termV[10][4]=0.183; termV[10][5]=0.169; termV[10][6]=0.159; termV[10][7]=0.154; termV[10][8]=0.154; termV[10][9]=0.156; termV[10][10]=0.16; termV[10][11]=0.164; termV[10][12]=0.173;
termV[11][0]=0.227; termV[11][1]=0.212; termV[11][2]=0.197; termV[11][3]=0.187; termV[11][4]=0.179; termV[11][5]=0.166; termV[11][6]=0.156; termV[11][7]=0.151; termV[11][8]=0.149; termV[11][9]=0.15; termV[11][10]=0.153; termV[11][11]=0.157; termV[11][12]=0.165;
termV[12][0]=0.22; termV[12][1]=0.206; termV[12][2]=0.192; termV[12][3]=0.183; termV[12][4]=0.175; termV[12][5]=0.162; termV[12][6]=0.153; termV[12][7]=0.147; termV[12][8]=0.144; termV[12][9]=0.144; termV[12][10]=0.147; termV[12][11]=0.151; termV[12][12]=0.158;
termV[13][0]=0.211; termV[13][1]=0.197; termV[13][2]=0.185; termV[13][3]=0.176; termV[13][4]=0.168; termV[13][5]=0.156; termV[13][6]=0.147; termV[13][7]=0.142; termV[13][8]=0.138; termV[13][9]=0.138; termV[13][10]=0.14; termV[13][11]=0.144; termV[13][12]=0.151;
termV[14][0]=0.204; termV[14][1]=0.192; termV[14][2]=0.18; termV[14][3]=0.171; termV[14][4]=0.164; termV[14][5]=0.152; termV[14][6]=0.143; termV[14][7]=0.138; termV[14][8]=0.134; termV[14][9]=0.134; termV[14][10]=0.137; termV[14][11]=0.14; termV[14][12]=0.148;
termV[15][0]=0.2; termV[15][1]=0.187; termV[15][2]=0.176; termV[15][3]=0.167; termV[15][4]=0.16; termV[15][5]=0.148; termV[15][6]=0.14; termV[15][7]=0.135; termV[15][8]=0.131; termV[15][9]=0.132; termV[15][10]=0.135; termV[15][11]=0.139; termV[15][12]=0.146;
// create a capfloor volatility surface based upon tenors/strike/volatility
capFloorVolSurface = boost::shared_ptr<CapFloorTermVolSurface>(new
CapFloorTermVolSurface(0, calendar,
optionTenors,
strikes,
termV,
Following,
dayCounter));
// floating rate index
boost::shared_ptr<IborIndex> iborIndex(new Euribor6M(yieldTermStructure));
OptionletStripper* optionletStripper1 = new
OptionletStripper1(capFloorVolSurface,
iborIndex,
Null<Rate>(),
accuracy);
optionletStripper1->recalculate();
delete optionletStripper1;
Real seconds = timer.elapsed();
Integer hours = int(seconds/3600);
seconds -= hours * 3600;
Integer minutes = int(seconds/60);
seconds -= minutes * 60;
std::cout << " \nRun completed in ";
if (hours > 0)
std::cout << hours << " h ";
if (hours > 0 || minutes > 0)
std::cout << minutes << " m ";
std::cout << std::fixed << std::setprecision(0)
<< seconds << " s\n" << std::endl;
//// create an optionlet stripper based upon the capfloor volatility surface
//boost::shared_ptr<OptionletStripper> optionletStripper1(new
// OptionletStripper1(capFloorVolSurface,
// iborIndex,
// Null<Rate>(),
// accuracy));
//StrippedOptionletAdapter* pAdapter = new
// StrippedOptionletAdapter(optionletStripper1);
//pAdapter->performCalculations();
//delete pAdapter;
// create an optionlet adapter based upon the optionlet stripper
//boost::shared_ptr<StrippedOptionletAdapter> strippedOptionletAdapter =
// boost::shared_ptr<StrippedOptionletAdapter>(new
// StrippedOptionletAdapter(optionletStripper1));
//strippedOptionletAdapter->performCalculations();
} catch (std::exception& e) {
std::cout << e.what() << std::endl;
return 1;
} catch (...) {
std::cout << "unknown error" << std::endl;
return 1;
}
std::cout << "Done";
}
On Fri, Apr 18, 2008 at 1:53 AM, Ferdinando Ametrano <
[hidden email]> wrote:
Hi Nathan
> I am looking at the optionletStripper1 class. As an input it uses a
> volatility term structure. Inside of it, it converts these volatilities into
> prices. Here in the US the ICAP service provides me with prices and no
> longer with volatilities (i.e. a grid of cap prices for given maturities and
> strikes). Any suggestions on how to handle this?
>
> My first thought was to extend the optionletStripper1 class to accept a
> matrix of prices. Or the CapFloorTermVolSurface could be renamed such that
> it can also hold prices. Any pointers on how to implement this in a way such
> that it can become part of the library would be appreciated.
I had to stop my volatility coding due to more urgent (yield curve)
priorities, but you're right that prices should be supported; given
the recent yield curve turmoil, brokers are kinda shifting towards
prices instead of vols.
I haven't thought in detail about the issue but I see the optionlet
stripper classes as disposable helper classes (btw this is the reason
why they are not fully documented, as they might undergo some major
refactoring). I would probably focus on CapFloorTermVolSurface and
expanding their interface to fully support both prices and vols
inspectors. When it comes to choice between prices and vols as input
parameters I would probably settle for prices, delegating vol handling
to some adapter class which would then turn vols into prices.
ciao -- Nando
-------------------------------------------------------------------------
This SF.net email is sponsored by the 2008 JavaOne(SM) Conference
Don't miss this year's exciting event. There's still time to save $100.
Use priority code J8TL2D2.
http://ad.doubleclick.net/clk;198757673;13503038;p?http://java.sun.com/javaone_______________________________________________
QuantLib-users mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/quantlib-users