-
Notifications
You must be signed in to change notification settings - Fork 50
/
Copy pathRQuantlib.R
203 lines (163 loc) · 8.1 KB
/
RQuantlib.R
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
stopifnot(require(RQuantLib))
## values from Quantlib's test-suite
## Reference: Haug, Option Pricing Formulas, McGraw-Hill, 1998
##
## and generally sourced from the code in the test-suite/
## directory of the QuantLib distribution
## europeanoption.cpp: call value == 2.1334
print(EuropeanOption("call", underlying=60, strike=65, div=0, riskFree=0.08,
maturity=0.25, vol=0.3), digits=5)
## europeanoption.cpp: put value == 2.4648
print(EuropeanOption("put", underlying=100, strike=95, div=0.05, riskFree=0.1,
maturity=0.5, vol=0.2), digits=5)
## europeanoption.cpp: call delta == 0.5946
print(EuropeanOption("call", underlying=105, strike=100,div=0.1,riskFree=0.1,
maturity=0.5, vol=0.36), digits=4)
## europeanoption.cpp: put delta == -0.3566
print(EuropeanOption("put", underlying=105, strike=100,div=0.1,riskFree=0.1,
maturity=0.5, vol=0.36), digits=4)
## europeanoption.cpp: call gamma == 0.0278
print(EuropeanOption("call", underlying=55, strike=60,div=0.0,riskFree=0.1,
maturity=0.75, vol=0.30), digits=4)
## europeanoption.cpp: put gamma == 0.0278
print(EuropeanOption("put", underlying=55, strike=60,div=0.0,riskFree=0.1,
maturity=0.75, vol=0.30), digits=4)
## europeanoption.cpp: call vega == 18.9358
print(EuropeanOption("call", underlying=55, strike=60,div=0.0,riskFree=0.1,
maturity=0.75, vol=0.30), digits=4)
## europeanoption.cpp: put vega == 18.9358
print(EuropeanOption("put", underlying=55, strike=60,div=0.0,riskFree=0.1,
maturity=0.75, vol=0.30), digits=4)
## americanoption.cpp: call value == 10.0089 -- we show 10.00606
print(AmericanOption("call", underlying=110, strike=100, div=0.1, riskFree=0.1,
maturity=0.1, vol=0.15), digits=5)
## americanoption.cpp: put value == 0.3159
print(AmericanOption("call", underlying=90, strike=100, div=0.1, riskFree=0.1,
maturity=0.1, vol=0.25), digits=5)
# Discrete dividend
## europeanoption.cpp: call value == 3.67
## Reference pg. 253 - Hull 5th ed Exercise 12.8 - From QuantLib tests
print(EuropeanOption("call", underlying=40, strike=40, div=0, riskFree=0.09,
maturity=0.5, vol=0.3,
discreteDividends = c(0.5, 0.5),
discreteDividendsTimeUntil = c(2/12, 5/12)), digits=5)
## americanoption.cpp: call value == 3.72 (Hull) -- we show 3.75
## Reference p. 256 - Hull 5th ed. Exercise 12.9 using (flawed) Roll, Geske, Whaley formula
print(AmericanOption("call", underlying=40, strike=40, div=0, riskFree=0.09,
maturity=0.5, vol=0.3,
engine = "CrankNicolson",
discreteDividends = c(0.5, 0.5),
discreteDividendsTimeUntil = c(2/12, 5/12)), digits=5)
## barrier: down and out call == 9.0246
print(BarrierOption("downout", barrier=95, rebate=3, type="call",
strike=90, underlying=100, div=0.04, riskF=0.08,
mat=0.5, vol=0.25), digits=4)
## barrier: down and in call == 7.7627
print(BarrierOption("downin", barrier=95, rebate=3, type="call",
strike=90, underlying=100, div=0.04, riskF=0.08,
mat=0.5, vol=0.25), digits=4)
## binary aka digital: put == 2.6710
print(BinaryOption(binType="cash", type="put", excType="european",
strike=80, underl=100, div=0.06, r=0.06,
mat=0.75, vol=0.35, cash=10), digits=4)
## asianoption.cpp: put == 4.6922 (from testAnalyticContinuousGeometricAveragePrice())
print( AsianOption("geometric", "put", underlying=80, strike=85, div=-0.03, riskFree=0.05, maturity=0.25, vol=0.2))
#.onWindows <- .Platform$OS.type == "windows"
## simple call with unnamed parameters
bond <- list(faceAmount=100,issueDate=as.Date("2004-11-30"),
maturityDate=as.Date("2008-11-30"), redemption=100 )
dateparams <-list(settlementDays=1, calendar="UnitedStates/GovernmentBond", businessDayConvention='Unadjusted')
discountCurve.param <- list(tradeDate=as.Date('2002-2-15'),
settleDate=as.Date('2002-2-15'),
dt=0.25,
interpWhat='discount', interpHow='loglinear')
discountCurve <- DiscountCurve(discountCurve.param, list(flat=0.05))
ZeroCouponBond(bond, discountCurve, dateparams)
## bond.cpp: examples from Fixed Income page of Matlab
ZeroYield(95, 100, as.Date("1993-6-24"), as.Date("1993-11-1"))
## bond.cpp: test theoretical price of bond by its yield
ZeroPriceByYield(0.1478, 100, as.Date("1993-6-24"), as.Date("1993-11-1"))
## bond.cpp: test theoretical yield of a fixed rate bond, = 0.0307
FixedRateBondYield(,99.282, 100000, as.Date("2004-11-30"), as.Date("2008-11-30"), 3, , c(0.02875), , , , ,as.Date("2004-11-30"))
## bond.cpp: test theoretical price of a fixed rate bond = 99.2708
FixedRateBondPriceByYield(,0.0307, 100000, as.Date("2004-11-30"), as.Date("2008-11-30"), 3, , c(0.02875), , , , ,as.Date("2004-11-30"))
## bond.cpp
## Simple call with a flat curve
bond <- list(settlementDays=1,
issueDate=as.Date("2004-11-30"),
faceAmount=100,
dayCounter='Thirty360',
paymentConvention='Unadjusted')
schedule <- list(effectiveDate=as.Date("2004-11-30"),
maturityDate=as.Date("2008-11-30"),
period='Semiannual',
calendar='UnitedStates/GovernmentBond',
businessDayConvention='Unadjusted',
terminationDateConvention='Unadjusted',
dateGeneration='Forward',
endOfMonth=1)
calc=list(dayCounter='Actual360',
compounding='Compounded',
freq='Annual',
durationType='Modified')
coupon.rate <- c(0.02875)
params <- list(tradeDate=as.Date('2002-2-15'),
settleDate=as.Date('2002-2-19'),
dt=.25,
interpWhat="discount",
interpHow="loglinear")
discountCurve.flat <- DiscountCurve(params, list(flat=0.05))
FixedRateBond(bond,
coupon.rate,
schedule,
calc,
discountCurve=discountCurve.flat)
## Same bond calculated from yield rather than from the discount curve
yield <- 0.02
FixedRateBond(bond,
coupon.rate,
schedule,
calc,
yield=yield)
#same example with clean price
price <- 103.31
FixedRateBond(bond,
coupon.rate,
schedule,
calc,
price = price)
## bond.cpp FloatingRateBond, following test-suite/bonds.cpp
bond <- list(faceAmount=100, issueDate=as.Date("2004-11-30"),
maturityDate=as.Date("2008-11-30"), redemption=100,
effectiveDate=as.Date("2004-11-30"))
dateparams <- list(settlementDays=1, calendar="UnitedStates/GovernmentBond",
dayCounter = 'ActualActual', period=2,
businessDayConvention = 1, terminationDateConvention=1,
dateGeneration=0, endOfMonth=0, fixingDays = 1)
gearings <- spreads <- caps <- floors <- vector()
params <- list(tradeDate=as.Date('2002-2-15'),
settleDate=as.Date('2002-2-19'),
dt=.25,
interpWhat="discount",
interpHow="loglinear")
tsQuotes <- list(d1w =0.0382,
d1m =0.0372,
fut1=96.2875,
fut2=96.7875,
fut3=96.9875,
fut4=96.6875,
fut5=96.4875,
fut6=96.3875,
fut7=96.2875,
fut8=96.0875,
s3y =0.0398,
s5y =0.0443,
s10y =0.05165,
s15y =0.055175)
## when both discount and libor curves are flat.
discountCurve.flat <- DiscountCurve(params, list(flat=0.05))
termstructure <- DiscountCurve(params, list(flat=0.03))
iborIndex.params <- list(type="USDLibor", length=6,
inTermOf="Month", term=termstructure)
FloatingRateBond(bond, gearings, spreads, caps, floors,
iborIndex.params, discountCurve.flat, dateparams)