Ставки обмена по номиналу QuantLib на нулевые ставки по обмену номиналом - PullRequest
1 голос
/ 29 мая 2020

Я построил кривую без купона на основе общей кривой ставки свопа c по номиналу ( Шаг 1 ), и я пытаюсь восстановить кривую свопа из кривой без купона ( Шаг 2 ).

Шаг 1 работает, но не Шаг 2. Я получаю близкие цитаты, но они не совсем совпадают. Кто-нибудь знает, что не так в моем Шаге 2?

Я предполагаю, что это не из-за проблем с календарем, поскольку я использую теоретический календарь, счетчик дней и индекс без каких-либо корректировок.

Вот мой код:

ШАГ 1:

# define constants
face_amount = 100
settlementDays = 0
calendar = ql.NullCalendar()
fixedLegAdjustment = ql.Unadjusted
floatingLegAdjustment = ql.Unadjusted
fixedLegDayCounter = ql.SimpleDayCounter()
floatingLegDayCounter = ql.SimpleDayCounter()
fixedLegFrequency = ql.Semiannual
end_of_month = False
floating_rate = ql.IborIndex("MyIndex", ql.Period(3, ql.Months), settlementDays, ql.USDCurrency(), calendar, floatingLegAdjustment, end_of_month, floatingLegDayCounter)

# irs is a DataFrame with one line and the column as maturities (from 3M to 120M)
deposits = [irs.columns[0]]
swaps = irs.columns[1:]

# curve dates
zero_rates = {}
curve_date = ql.DateParser.parseFormatted(str("2017-01-01"), "%Y-%m-%d")
ql.Settings.instance().evaluationDate = curve_date
spot_date = calendar.advance(curve_date, settlementDays, ql.Days)

# deposit helper
deposit_helpers_mat = []
for tenor in deposits:
    deposit_helpers_mat.append([ql.Period(int(tenor), ql.Months), ql.QuoteHandle(ql.SimpleQuote(irs[int(tenor)] / 100))])

deposit_helper = [ql.DepositRateHelper(tenors_deposit, settlementDays, calendar, fixedLegAdjustment, end_of_month, fixedLegDayCounter) for tenors_deposit, deposit_rates in deposit_helpers_mat]

# swap helper
swap_helpers_mat = []
for tenor in swaps:
    swap_helpers_mat.append([ql.Period(int(tenor), ql.Months), ql.QuoteHandle(ql.SimpleQuote(irs[int(tenor)] / 100))])

swap_helper = [ql.SwapRateHelper(swap_rates, tenors_swap, calendar, fixedLegFrequency, fixedLegAdjustment, fixedLegDayCounter, floating_rate) for tenors_swap, swap_rates in swap_helpers_mat]

# aggregate helpers
helper = deposit_helper + swap_helper

# build curve
zc_curve = ql.PiecewiseCubicZero(curve_date, helper, ql.SimpleDayCounter())
zero_rate = []
tenors = []
# loop over maturities
for tenor in np.arange(3, 120 + 1, 3):
    maturity_date = calendar.advance(spot_date, ql.Period(int(tenor), ql.Months))
    zero_rate_curve = (zc_curve.zeroRate(maturity_date, ql.SimpleDayCounter(), ql.Compounded, ql.Annual).rate()* 100)
    zero_rate.append(zero_rate_curve)
    tenors.append(tenor)

# build the zero curve representation into a DataFrame
zero_rates = pd.DataFrame(np.transpose(list(zip(zero_rate))), columns=list(tenors))

ШАГ 2:

# constant
fixedRate = 0.02
spread =0
TENORS = np.arange(3, 120 + 1, 3)

# pre-allocate
irs_rates = {}
# calculate dates
curve_date = ql.DateParser.parseFormatted(str("2017-01-01"), "%Y-%m-%d")
ql.Settings.instance().evaluationDate = curve_date
spot_date = calendar.advance(curve_date, settlementDays, ql.Days)

# zero curve
irs_rate = []
tenors = []
maturity_dates = []
zc_rates = []
# loop over maturities
for tenor in TENORS:
    # maturity date
    maturity_date = calendar.advance(spot_date, ql.Period(int(tenor), ql.Months))
    # gather maturity dates
    maturity_dates.append(maturity_date)
    # gather zc rates
    zc_rates.append(zero_rates[int(tenor)] / 100)


# build zero coupon curve object
zero_curve = ql.YieldTermStructureHandle(ql.CubicZeroCurve(maturity_dates, zc_rates, fixedLegDayCounter, calendar))
# libor curve
libor_curve = ql.YieldTermStructureHandle(ql.CubicZeroCurve(maturity_dates, zc_rates, floatingLegDayCounter, calendar))
# floating rate
floating_rate = ql.IborIndex("MyIndex", ql.Period(3, ql.Months), settlementDays, ql.USDCurrency(), calendar, floatingLegAdjustment, end_of_month, floatingLegDayCounter, libor_curve)

# build swap curve
# loop over maturities
j = 0
for maturity in maturity_dates:
    # fixed leg tenor
    fixedLegTenor = ql.Period(3, ql.Months)
    # fixed leg coupon schedule
    fixedLegSchedule = ql.Schedule(spot_date, maturity, fixedLegTenor, calendar, fixedLegAdjustment, fixedLegAdjustment, ql.DateGeneration.Forward, end_of_month)

    # floating leg tenor
    floatingLegTenor = ql.Period(3, ql.Months)
    # floating leg coupon schedule
    floatingLegSchedule = ql.Schedule(spot_date, maturity, floatingLegTenor, calendar, floatingLegAdjustment, floatingLegAdjustment, ql.DateGeneration.Forward, end_of_month)

    # build swap pricer
    swap_rate = ql.VanillaSwap(ql.VanillaSwap.Payer, face_amount, fixedLegSchedule, fixedRate, fixedLegDayCounter, floatingLegSchedule, floating_rate, spread, floatingLegDayCounter)

    # build swap curve
    swap_curve = ql.DiscountingSwapEngine(zero_curve)
    # get swap rate
    swap_rate.setPricingEngine(swap_curve)

    # gather par irs rate
    irs_rate.append(swap_rate.fairRate() * 100)
    # gather irs tenor
    tenor = int(TENORS[j])
    j = j + 1
    tenors.append(tenor)
    # build the swap curve representation into a DataFrame
    irs_rates = pd.DataFrame(np.transpose(list(zip(irs_rate))), columns=list(tenors))
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...