Skip to content
All library documents

How QuantLib IBOR Index Calendars Affect Forecast Fixings

Article Quant Q&A · Author: Richael Kam

Summary

The document explains the relationship between QuantLib’s generic IBOR index class and specialized indices such as Euribor and USD LIBOR. The generic class accepts parameters including currency, tenor, fixing calendar, business-day convention, and day-count convention. The specialized classes supply their own market conventions while inheriting the rate calculation machinery, so differences in output need not indicate different calculation formulas.

The example compares forward fixings from a generic USD index, Euribor, and USD LIBOR using a flat curve. The accepted answer attributes the small discrepancy between the generic index and USD LIBOR to their fixing calendars: the calendar determines the start and end dates for the forecast period, and holidays in the US and UK shift those dates differently. Euribor and USD LIBOR happen to return the same value in the example, but their market conventions are not thereby interchangeable. The explanation is specific to the supplied setup and notes that USD LIBOR’s calendar is historical context; it does not discuss benchmark transition or broader curve construction.

Key ideas

  • IborIndex is the generic base class, while named IBOR indices provide market-specific conventions.
  • Specialized indices inherit the calculation logic but use configured calendars and day-count conventions.
  • Different holiday calendars can shift forecast accrual dates and produce slightly different fixings.
  • Matching outputs in one example do not imply that two named benchmarks share all conventions.

Tags

Full text
# What's the difference between ql.Euribor, ql.Libor, ql.Iborindex? like are their calculation share the same machanism?


# What's the difference between ql.Euribor, ql.Libor, ql.Iborindex? like are their calculation share the same machanism?












```
# Here is the code below, I use different function calculate the answer, and their result are different.

# Define the evaluation date
ql.Settings.instance().evaluationDate = ql.Date(23, 9, 2024)
 
# Set notional and coupon rate
notional = 1000000
coupon_rate = 0.02
 
# Set dates for cash flow testing
start_date = ql.Date(23, 9, 2023)
end_date = ql.Date(23, 9, 2025)
 
# Schedule setup for the fixed leg (semi-annual payments)
calendar = ql.UnitedStates(ql.UnitedStates.GovernmentBond)  # Specify the market type
schedule = ql.Schedule(start_date, end_date, ql.Period(ql.Semiannual),
                       calendar, ql.ModifiedFollowing, ql.ModifiedFollowing, 
                       ql.DateGeneration.Forward, False)
 
# Set up a fixed-rate bond for comparison
fixed_leg = ql.FixedRateLeg(schedule, ql.Actual360(), [notional], [coupon_rate])
 
# Create discount curve (constant flat rate for simplicity)
flat_rate = ql.FlatForward(0, ql.NullCalendar(), ql.QuoteHandle(ql.SimpleQuote(0.03)), ql.Actual360())
discount_curve = ql.YieldTermStructureHandle(flat_rate)
 
# Compare ql.IborIndex, ql.Euribor, ql.Libor
# 1. IborIndex (3-month USD)
ibor_index = ql.IborIndex("Ibor", ql.Period(3, ql.Months), 2, ql.USDCurrency(), calendar, ql.ModifiedFollowing, False, ql.Actual360(), discount_curve)
 
# 2. Euribor (3-month)
euribor_index = ql.Euribor3M(discount_curve)
 
# 3. Libor (3-month USD)
libor_index = ql.USDLibor(ql.Period(3, ql.Months), discount_curve)
 
# Extract forward rates from each index
ibor_rate = ibor_index.fixing(ql.Date(23, 9, 2024))
euribor_rate = euribor_index.fixing(ql.Date(23, 9, 2024))
libor_rate = libor_index.fixing(ql.Date(23, 9, 2024))
 
print(f"Ibor Index Rate: {ibor_rate}")
print(f"Euribor Rate: {euribor_rate}")
print(f"Libor Rate: {libor_rate}")

# output:
'''
Ibor Index Rate: 0.03011529445304053
Euribor Rate: 0.030116550895258113
Libor Rate: 0.030116550895258113
'''
```
```

## Answer by Luigi Ballabio (score 4, accepted)

https://quant.stackexchange.com/a/81083

`IborIndex` is the generic base class. `Euribor` and `USDLibor` specialize it by specifying the fixing calendar, the day count convention and all the other parameters you're passing to the `IborIndex` constructor in your example. The calculations are inherited from `IborIndex` and are the same for all three.

The slight difference you see is due to the fact that the fixing calendar for USD LIBOR is (or, I should say, was) a combination of the US calendar and of the UK calendar, where the LIBOR was fixed. Thus, when asked for the fixing for September 23, your `ibor_index` will forecast the rate from September 25 to December 26 (because Dec. 25, Christmas, is a US holiday) while `libor_index` will forecast the rate from September 25 to December 27 (because Dec. 25 and 26 are both holidays in the UK).

Shown in full with attribution under the source's licence. Licence: CC BY-SA 4.0 (Stack Exchange)

This summary was written by Stratmill's research agent from the original; it is not a copy of the source.