QuantLib-SWIG icon indicating copy to clipboard operation
QuantLib-SWIG copied to clipboard

The cash flows of FloatingRateBond are different from my expectation

Open xuruilong100 opened this issue 5 years ago • 3 comments
trafficstars

If the curve is flat.

import QuantLib as ql
import prettytable as pt
from datetime import date

print(ql.__version__)

'''
1.19
'''

today = ql.Date(28, ql.July, 2020)
ql.Settings.instance().evaluationDate = today

settlementDays = 1
faceAmount = 100.0

effectiveDate = ql.Date(9, ql.June, 2020)
terminationDate = ql.Date(9, ql.June, 2025)
tenor = ql.Period(ql.Quarterly)
calendar = ql.China(ql.China.IB)
convention = ql.Unadjusted
terminationDateConvention = convention
rule = ql.DateGeneration.Backward
endOfMonth = False

schedule = ql.Schedule(
    effectiveDate,
    terminationDate,
    tenor,
    calendar,
    convention,
    terminationDateConvention,
    rule,
    endOfMonth)

nextLpr = 4.0 / 100.0
fixedLpr = 4.0 / 100.0

compounding = ql.Compounded
frequency = ql.Quarterly
accrualDayCounter = ql.ActualActual(ql.ActualActual.Bond, schedule)
dayCounter = ql.ActualActual(ql.ActualActual.Bond, schedule)
paymentConvention = ql.Unadjusted
fixingDays = 1
gearings = ql.DoubleVector(1, 1.0)
spreads = ql.DoubleVector(1, 0.0 / 100.0)

lprTermStructure = ql.YieldTermStructureHandle(
    ql.FlatForward(
        settlementDays,
        calendar,
        nextLpr,
        dayCounter,
        compounding,
        frequency))

lpr3m = ql.IborIndex(
    'LPR1Y',
    ql.Period(ql.Quarterly),
    settlementDays,
    ql.CNYCurrency(),
    calendar,
    convention,
    endOfMonth,
    dayCounter,
    lprTermStructure)

lpr3m.addFixing(ql.Date(8, ql.June, 2020), fixedLpr)

bond = ql.FloatingRateBond(
    settlementDays,
    faceAmount,
    schedule,
    lpr3m,
    accrualDayCounter,
    convention,
    fixingDays,
    gearings,
    spreads)

cfTab = pt.PrettyTable(['Date', 'Amount'])

for c in bond.cashflows():
    dt = date(
        c.date().year(),
        c.date().month(),
        c.date().dayOfMonth())
    cfTab.add_row([dt, c.amount()])

print(cfTab)

'''
1.19
+------------+--------------------+
|    Date    |       Amount       |
+------------+--------------------+
| 2020-09-09 |        1.0         |
| 2020-12-09 | 1.0000000000000009 |
| 2021-03-09 | 1.0000000000000009 |
| 2021-06-09 | 1.0000000000000009 |
| 2021-09-09 | 1.000000000000023  |
| 2021-12-09 | 0.9999999999999787 |
| 2022-03-09 | 1.0000000000000009 |
| 2022-06-09 | 1.0000000000000009 |
| 2022-09-09 | 1.0000000000000009 |
| 2022-12-09 | 1.0000000000000009 |
| 2023-03-09 | 1.0000000000000009 |
| 2023-06-09 | 1.0000000000000009 |
| 2023-09-09 | 1.000109533621161  |
| 2023-12-09 | 1.0000000000000009 |
| 2024-03-09 | 0.9999988095049638 |
| 2024-06-09 | 0.9999458343873505 |
| 2024-09-09 | 0.9999458343873505 |
| 2024-12-09 | 1.0000000000000009 |
| 2025-03-09 | 1.0000541695215703 |
| 2025-06-09 | 0.9999458343873505 |
| 2025-06-09 |       100.0        |
+------------+--------------------+
'''

The cash flow at 2023-09-09 is quite different from my expectation, I think it should be 1.0000000000000009.

xuruilong100 avatar Aug 18 '20 01:08 xuruilong100

Thanks for posting! It might take a while before we look at your issue, so don't worry if there seems to be no feedback. We'll get to it.

boring-cyborg[bot] avatar Aug 18 '20 01:08 boring-cyborg[bot]

if you define your day counters without the schedule as parameter you will get the values you were expecting.

accrualDayCounter = ql.ActualActual(ql.ActualActual.Bond)
dayCounter = ql.ActualActual(ql.ActualActual.Bond)

nhaga avatar Aug 28 '20 11:08 nhaga

if you define your day counters without the schedule as parameter you will get the values you were expecting.

accrualDayCounter = ql.ActualActual(ql.ActualActual.Bond)
dayCounter = ql.ActualActual(ql.ActualActual.Bond)

Yes, you are right.

But the curve is flat, no matter how the forward rate is calculated, it should be 1.0.

The cash flows are created by FloatingLeg, I chack the code, it can not use refStart and refEnd in this case.

While, if I define day counters with the schedule, they can use refStart and refEnd, please see here: https://quant.stackexchange.com/questions/12707/pricing-a-fixedratebond-in-quantlib-yield-vs-termstructure

So, there is inconsistence.

xuruilong100 avatar Aug 31 '20 14:08 xuruilong100