BondFuture#
- class rateslib.instruments.BondFuture(coupon, delivery, basket, nominal=NoInput.blank, contracts=NoInput.blank, calendar=NoInput.blank, currency=NoInput.blank, calc_mode=NoInput.blank)#
Bases:
Sensitivities
Create a bond future derivative.
- Parameters:
coupon (float) – The nominal coupon rate set on the contract specifications.
delivery (datetime or 2-tuple of datetimes) – The delivery window first and last delivery day, or a single delivery day.
basket (tuple of FixedRateBond) – The bonds that are available as deliverables.
nominal (float, optional) – The nominal amount of the contract.
contracts (int, optional) – The number of contracts owned or short.
calendar (str, optional) – The calendar to define delivery days within the delivery window.
currency (str, optional) – The currency (3-digit code) of the settlement contract.
calc_mode (str, optional) – The method to calculate conversion factors. See notes.
Notes
Conversion factors (CFs)
calc_mode
are:“ytm” which calculates the CF as the clean price percent of par with the bond having a yield-to-maturity on the first delivery day in the delivery window.
“ust_short” which applies to CME 2y, 3y and 5y treasury futures. See
CME Treasury Conversion Factors
.“ust_long” which applies to CME 10y and 30y treasury futures.
Examples
The
dlv()
method is a summary method which displays many attributes simultaneously in a DataFrame. This example replicates the Bloomberg screen print in the publication The Futures Bond Basis: Second Edition (p77) by Moorad Choudhry. To replicate that publication exactly no calendar has been provided. A more modern Bloomberg would probably consider the London business day calendar and this would affect the metrics of the third bond to a small degree (i.e. set calendar=”ldn”)In [1]: kws = dict( ...: frequency="S", ...: ex_div=7, ...: convention="ActActICMA", ...: currency="gbp", ...: settle=1, ...: curves="gilt_curve" ...: ) ...: In [2]: bonds = [ ...: FixedRateBond(dt(1999, 1, 1), dt(2009, 12, 7), fixed_rate=5.75, **kws), ...: FixedRateBond(dt(1999, 1, 1), dt(2011, 7, 12), fixed_rate=9.00, **kws), ...: FixedRateBond(dt(1999, 1, 1), dt(2010, 11, 25), fixed_rate=6.25, **kws), ...: FixedRateBond(dt(1999, 1, 1), dt(2012, 8, 6), fixed_rate=9.00, **kws), ...: ] ...: In [3]: prices=[102.732, 131.461, 107.877, 134.455] In [4]: ytms=[bond.ytm(price, dt(2000, 3, 16)) for bond, price in zip(bonds, prices)] In [5]: future = BondFuture( ...: delivery=(dt(2000, 6, 1), dt(2000, 6, 30)), ...: coupon=7.0, ...: basket=bonds, ...: nominal=100000, ...: contracts=10, ...: currency="gbp", ...: ) ...: In [6]: future.dlv( ...: future_price=112.98, ...: prices=[102.732, 131.461, 107.877, 134.455], ...: repo_rate=6.24, ...: settlement=dt(2000, 3, 16), ...: convention="Act365f", ...: ) ...: Out[6]: Bond Price YTM C.Factor Gross Basis Implied Repo Actual Repo Net Basis 0 5.750% 07-12-2009 102.73 5.38 0.91 -0.56 7.38 6.24 -0.34 1 9.000% 12-07-2011 131.46 5.27 1.15 1.24 3.56 6.24 1.03 2 6.250% 25-11-2010 107.88 5.28 0.94 1.12 2.20 6.24 1.28 3 9.000% 06-08-2012 134.46 5.19 1.16 3.18 -1.41 6.24 3.01
Various other metrics can be extracted in isolation including,
notional
, and conversion factors (cfs
),gross_basis()
,net_basis()
,implied_repo()
,ytm()
,duration()
,convexity()
,ctd_index()
,In [7]: future.cfs Out[7]: (0.9142254519590044, 1.152570524483184, 0.9449311626312817, 1.1619558330528528) In [8]: future.notional Out[8]: -1000000 In [9]: future.gross_basis( ...: future_price=112.98, ...: prices=prices, ...: ) ...: Out[9]: (-0.5571915623283274, 1.2435821438898813, 1.1186772459177803, 3.177229981688697) In [10]: future.net_basis( ....: future_price=112.98, ....: prices=prices, ....: repo_rate=6.24, ....: settlement=dt(2000, 3, 16), ....: delivery=dt(2000, 6, 30), ....: convention="Act365f" ....: ) ....: Out[10]: (-0.3436542561467206, 1.0336684511125043, 1.2758661359273589, 3.0103709249974315) In [11]: future.implied_repo( ....: future_price=112.98, ....: prices=prices, ....: settlement=dt(2000, 3, 16) ....: ) ....: Out[11]: (7.280230878873247, 3.5158540419955497, 2.1696209356561105, -1.3952912833468138) In [12]: future.ytm(future_price=112.98) Out[12]: (5.301960107610736, 5.339807671798653, 5.391831098248339, 5.437566603312508) In [13]: future.duration(future_price=112.98) Out[13]: (8.20178546111166, 8.501520935536226, 8.69035086967293, 9.041578306005354) In [14]: future.convexity(future_price=112.98) Out[14]: (0.7283734047262407, 0.8301477419758643, 0.8327576470105787, 0.9509416768492558) In [15]: future.ctd_index( ....: future_price=112.98, ....: prices=prices, ....: settlement=dt(2000, 3, 16) ....: ) ....: Out[15]: 0
As opposed to the analogue methods above, we can also use the digital methods,
npv()
,rate()
, but we need to create Curves and a Solver in the usual way.In [16]: gilt_curve = Curve( ....: nodes={ ....: dt(2000, 3, 15): 1.0, ....: dt(2009, 12, 7): 1.0, ....: dt(2010, 11, 25): 1.0, ....: dt(2011, 7, 12): 1.0, ....: dt(2012, 8, 6): 1.0, ....: }, ....: id="gilt_curve", ....: ) ....: In [17]: solver = Solver( ....: curves=[gilt_curve], ....: instruments=[(b, (), {"metric": "ytm"}) for b in bonds], ....: s=ytms, ....: id="gilt_solver", ....: instrument_labels=["5.75% '09", "9% '11", "6.25% '10", "9% '12"], ....: ) ....: SUCCESS: `func_tol` reached after 6 iterations (levenberg_marquardt), `f_val`: 1.4029004547912916e-13, `time`: 0.1202s
Sensitivities are also available;
delta()
gamma()
.In [18]: future.delta(solver=solver) Out[18]: local_ccy gbp display_ccy gbp type solver label instruments gilt_solver 5.75% '09 -814.17 9% '11 -0.00 6.25% '10 0.00 9% '12 0.00
The delta of a BondFuture is individually assigned to the CTD. If the CTD changes the delta is reassigned.
In [19]: solver.s = [5.3842, 5.2732, 5.2755, 5.52] In [20]: solver.iterate() SUCCESS: `func_tol` reached after 6 iterations (levenberg_marquardt), `f_val`: 2.316093834907418e-16, `time`: 0.1362s In [21]: future.delta(solver=solver) Out[21]: local_ccy gbp display_ccy gbp type solver label instruments gilt_solver 5.75% '09 32.57 9% '11 -0.00 6.25% '10 -0.00 9% '12 -928.63 In [22]: future.gamma(solver=solver) Out[22]: type instruments solver gilt_solver label 5.75% '09 9% '11 6.25% '10 9% '12 local_ccy display_ccy type solver label gbp gbp instruments gilt_solver 5.75% '09 -0.00 -0.00 -0.00 -0.03 9% '11 -0.00 0.00 -0.00 0.00 6.25% '10 -0.00 -0.00 0.00 0.00 9% '12 -0.03 0.00 0.00 0.99
Attributes Summary
Return the conversion factors for each bond in the ordered
basket
.Return the notional as number of contracts multiplied by contract nominal.
Methods Summary
cashflows_table
([curves, solver, fx, base])cms
(prices, settlement, shifts[, delivery, ...])Perform CTD multi-security analysis.
convexity
(future_price[, delivery])Return the second derivative of
price
w.r.t.ctd_index
(future_price, prices, settlement)Determine the index of the CTD in the basket from implied repo rate.
delta
(*args, **kwargs)Calculate the delta of the Instrument.
dlv
(future_price, prices, repo_rate, settlement)Return an aggregated DataFrame of metrics similar to the Bloomberg DLV function.
duration
(future_price[, metric, delivery])Return the (negated) derivative of
price
w.r.t.gamma
(*args, **kwargs)Calculate the gamma of the Instrument.
gross_basis
(future_price, prices[, ...])Calculate the gross basis of each bond in the basket.
implied_repo
(future_price, prices, settlement)Calculate the implied repo of each bond in the basket using the proceeds method.
net_basis
(future_price, prices, repo_rate, ...)Calculate the net basis of each bond in the basket via the proceeds method of repo.
npv
([curves, solver, fx, base, local])Determine the monetary value of the bond future position.
rate
([curves, solver, fx, base, metric, ...])Return various pricing metrics of the security calculated from
Curve
s.ytm
(future_price[, delivery])Calculate the yield-to-maturity of the bond future.
Attributes Documentation
- cfs#
Return the conversion factors for each bond in the ordered
basket
.- Return type:
tuple
Notes
This method uses the traditional calculation of obtaining a clean price for each bond on the first delivery date assuming the yield-to-maturity is set as the nominal coupon of the bond future, and scaled to 100.
Warning
Some exchanges, such as EUREX, specify their own conversion factors’ formula which differs slightly in the definition of yield-to-maturity than the implementation offered by rateslib. This results in small differences and is potentially explained in the way dates, holidays and DCFs are handled by each calculator.
For ICE-LIFFE and gilt futures the methods between the exchange and rateslib align which results in accurate values. Official values can be validated against the document
ICE-LIFFE Jun23 Long Gilt
.For an equivalent comparison with values which do not exactly align see
EUREX Jun23 Bond Futures
.Examples
In [1]: kws = dict( ...: stub="ShortFront", ...: frequency="S", ...: calendar="ldn", ...: currency="gbp", ...: convention="ActActICMA", ...: ex_div=7, ...: settle=1, ...: ) ...: In [2]: bonds = [ ...: FixedRateBond(dt(1999, 1, 1), dt(2009, 12, 7), fixed_rate=5.75, **kws), ...: FixedRateBond(dt(1999, 1, 1), dt(2011, 7, 12), fixed_rate=9.00, **kws), ...: FixedRateBond(dt(1999, 1, 1), dt(2010, 11, 25), fixed_rate=6.25, **kws), ...: FixedRateBond(dt(1999, 1, 1), dt(2012, 8, 6), fixed_rate=9.00, **kws), ...: ] ...: In [3]: future = BondFuture( ...: delivery=(dt(2000, 6, 1), dt(2000, 6, 30)), coupon=7.0, basket=bonds ...: ) ...: In [4]: future.cfs Out[4]: (0.9142254519590044, 1.152570524483184, 0.9449311626312817, 1.1619558330528528)
- notional#
Return the notional as number of contracts multiplied by contract nominal.
- Return type:
float
Methods Documentation
- cashflows_table(curves=NoInput.blank, solver=NoInput.blank, fx=NoInput.blank, base=NoInput.blank)#
- cms(prices, settlement, shifts, delivery=NoInput.blank, dirty=False)#
Perform CTD multi-security analysis.
- Parameters:
prices (sequence of float, Dual, Dual2) – The prices of the bonds in the deliverable basket (ordered).
settlement (datetime) – The settlement date of the bonds.
shifts (list of float) – The scenarios to analyse.
delivery (datetime, optional) – The date of the futures delivery. If not given uses the final delivery day.
dirty (bool) – Whether the bond prices are given including accrued interest. Default is False.
- Return type:
DataFrame
Notes
This method only operates when the CTD basket has multiple securities
- convexity(future_price, delivery=NoInput.blank)#
Return the second derivative of
price
w.r.t.ytm
.- Parameters:
future_price (float) – The price of the future.
delivery (datetime, optional) – The delivery date of the contract. If not given uses the last delivery day in the delivery window.
- Return type:
float
See also
FixedRateBond.convexity
Calculate the convexity of a FixedRateBond.
Example
In [1]: risk = future.duration(112.98) In [2]: convx = future.convexity(112.98) In [3]: convx Out[3]: (0.7283734047262407, 0.8301477419758643, 0.8327576470105787, 0.9509416768492558)
Observe the change in risk duration when the prices is increased by 1bp.
In [4]: future.duration(112.98) Out[4]: (8.20178546111166, 8.501520935536226, 8.69035086967293, 9.041578306005354) In [5]: future.duration(112.98 + risk[0] / 100) Out[5]: (8.20906950450452, 8.509530163283793, 8.698210628688548, 9.050204961493332)
- ctd_index(future_price, prices, settlement, delivery=NoInput.blank, dirty=False, ordered=False)#
Determine the index of the CTD in the basket from implied repo rate.
- Parameters:
future_price (float) – The price of the future.
prices (sequence of float, Dual, Dual2) – The prices of the bonds in the deliverable basket (ordered).
settlement (datetime) – The settlement date of the bonds.
delivery (datetime, optional) – The date of the futures delivery. If not given uses the final delivery day.
dirty (bool) – Whether the bond prices are given including accrued interest.
ordered (bool, optional) – Whether to return the sorted order of CTD indexes and not just a single index for the specific CTD.
- Return type:
int
- delta(*args, **kwargs)#
Calculate the delta of the Instrument.
For arguments see
Sensitivities.delta()
.
- dlv(future_price, prices, repo_rate, settlement, delivery=NoInput.blank, convention=NoInput.blank, dirty=False)#
Return an aggregated DataFrame of metrics similar to the Bloomberg DLV function.
- Parameters:
future_price (float, Dual, Dual2) – The price of the future.
prices (sequence of float, Dual, Dual2) – The prices of the bonds in the deliverable basket (ordered).
repo_rate (float, Dual, Dual2 or list/tuple of such) – The repo rates of the bonds to delivery.
settlement (datetime) – The settlement date of the bonds.
delivery (datetime, optional) – The date of the futures delivery. If not given uses the final delivery day.
convention (str, optional) – The day count convention applied to the repo rates.
dirty (bool) – Whether the bond prices are given including accrued interest. Default is False.
- Return type:
DataFrame
- duration(future_price, metric='risk', delivery=NoInput.blank)#
Return the (negated) derivative of
price
w.r.t.ytm
.- Parameters:
future_price (float) – The price of the future.
metric (str) – The specific duration calculation to return. See notes.
delivery (datetime, optional) – The delivery date of the contract.
- Return type:
float
See also
FixedRateBond.duration
Calculation the risk of a FixedRateBond.
Example
In [1]: risk = future.duration(112.98) In [2]: risk Out[2]: (8.20178546111166, 8.501520935536226, 8.69035086967293, 9.041578306005354)
The difference in yield is shown to be 1bp for the CTD (index: 0) when the futures price is adjusted by the risk amount.
In [3]: future.ytm(112.98) Out[3]: (5.301960107610736, 5.339807671798653, 5.391831098248339, 5.437566603312508) In [4]: future.ytm(112.98 + risk[0] / 100) Out[4]: (5.29196454544367, 5.330164780141207, 5.382397556462216, 5.42849974015735)
- gamma(*args, **kwargs)#
Calculate the gamma of the Instrument.
For arguments see
Sensitivities.gamma()
.
- gross_basis(future_price, prices, settlement=NoInput.blank, dirty=False)#
Calculate the gross basis of each bond in the basket.
- Parameters:
future_price (float, Dual, Dual2) – The price of the future.
prices (sequence of float, Dual, Dual2) – The prices of the bonds in the deliverable basket (ordered).
settlement (datetime) – The settlement date of the bonds, required only if
dirty
is True.dirty (bool) – Whether the bond prices are given including accrued interest.
- Return type:
tuple
- implied_repo(future_price, prices, settlement, delivery=NoInput.blank, convention=NoInput.blank, dirty=False)#
Calculate the implied repo of each bond in the basket using the proceeds method.
- Parameters:
future_price (float, Dual, Dual2) – The price of the future.
prices (sequence of float, Dual, Dual2) – The prices of the bonds in the deliverable basket (ordered).
settlement (datetime) – The settlement date of the bonds.
delivery (datetime, optional) – The date of the futures delivery. If not given uses the final delivery day.
convention (str, optional) – The day count convention used in the rate.
dirty (bool) – Whether the bond prices are given including accrued interest.
- Return type:
tuple
- net_basis(future_price, prices, repo_rate, settlement, delivery=NoInput.blank, convention=NoInput.blank, dirty=False)#
Calculate the net basis of each bond in the basket via the proceeds method of repo.
- Parameters:
future_price (float, Dual, Dual2) – The price of the future.
prices (sequence of float, Dual, Dual2) – The prices of the bonds in the deliverable basket (ordered).
repo_rate (float, Dual, Dual2 or list/tuple of such) – The repo rates of the bonds to delivery.
settlement (datetime) – The settlement date of the bonds, required only if
dirty
is True.delivery (datetime, optional) – The date of the futures delivery. If not given uses the final delivery day.
convention (str, optional) – The day count convention applied to the repo rates.
dirty (bool) – Whether the bond prices are given including accrued interest.
- Return type:
tuple
- npv(curves=NoInput.blank, solver=NoInput.blank, fx=NoInput.blank, base=NoInput.blank, local=False)#
Determine the monetary value of the bond future position.
This method is mainly included to calculate risk sensitivities. The monetary value of bond futures is not usually a metric worth considering. The profit or loss of a position based on entry level is a more common metric, however the initial value of the position does not affect the risk.
See
BaseDerivative.npv()
.
- rate(curves=NoInput.blank, solver=NoInput.blank, fx=NoInput.blank, base=NoInput.blank, metric='future_price', delivery=NoInput.blank)#
Return various pricing metrics of the security calculated from
Curve
s.- Parameters:
curves (Curve, str or list of such) –
A single
Curve
or id or a list of such. A list defines the following curves in the order:Forecasting
Curve
forleg1
.Discounting
Curve
forleg1
.
solver (Solver, optional) – The numerical
Solver
that constructsCurves
from calibrating instruments.fx (float, FXRates, FXForwards, optional) – The immediate settlement FX rate that will be used to convert values into another currency. A given float is used directly. If giving a
FXRates
orFXForwards
object, converts from local currency intobase
.base (str, optional) – The base currency to convert cashflows into (3-digit code), set by default. Only used if
fx
is anFXRates
orFXForwards
object.metric (str in {"future_price", "ytm"}, optional) – Metric returned by the method.
delivery (datetime, optional) – The date of the futures delivery. If not given uses the final delivery day.
- Return type:
Notes
This method determines the ‘futures_price’ and ‘ytm’ by assuming a net basis of zero and pricing from the cheapest to delivery (CTD).
- ytm(future_price, delivery=NoInput.blank)#
Calculate the yield-to-maturity of the bond future.