Existe una prima de liquidez entre las emisiones de tesorería on-the-run y las emisiones off-the-run de características similares. Por ello, al construir una curva de rendimiento, se suelen utilizar las emisiones on-the-run para calcular esta curva como representación del tipo libre de riesgo.
Parece ser una práctica académica y profesional común eliminar estos valores "especiales" (por cuestiones obvias) al construir la curva. Sin embargo, cuando se realiza un análisis de valor relativo entre estos bonos, se utilizan exclusivamente estos valores fuera de serie.
Por lo general, sigue habiendo discrepancias entre los temas muy experimentados.
- ¿Cómo son estas emisiones (por ejemplo, un bono original a 30 años con menos de 2 años hasta el vencimiento y un cupón muy alto) se incorporan a los cálculos de la curva de rendimiento cálculos de la curva de rendimiento?
- ¿Cómo puedo obtener un YTM significativo para este ejemplo de vencimiento?
Por ejemplo, el bono original a 30 años de vencimiento más cercano en la actualidad es:
912810EB0 - Nov15'18 9.0 - BID 101.14000 ASK 101.30600 Mark Yield 1.994%
(edición: este rendimiento es proporcionado por el corredor, pero parece razonable, por lo que su "matemática de bonos" no explotó como la mía).
He probado mis propias matemáticas de bonos y algunas calculadoras disponibles aquí: http://www.quantwolf.com/calculators/bondyieldcalc.html
def bond_ytm(bond):
price = float(bond['END OF DAY'])
par = 100.
T = bond['T']
t = pd.to_datetime(bond['date'])
if bond['SECURITY TYPE'] == 'MARKET BASED FRN':
freq = 4
else:
freq = 2
coupon = float(bond['RATE'].strip('%'))/freq
coupon_dates = get_coupon_dates(bond, afterDate=t)
# zero-coupon
if len(coupon_dates) == 0:
return (par/price)**(1/T) - 1.0
dt = dates_to_relative(coupon_dates, anchor=t)
def Px(Rate):
return price - (((par + coupon) / (1 + Rate/freq)**(T)) + ((coupon/Rate) * sum([(1 / (1+Rate/freq)**(time*freq)) for time in dt]) ))
ytm_func = lambda y: coupon*sum([1/(1+y/freq)**(time) for time in dt]) + 1/(1+y/freq)**(freq*T)
guess = coupon/par
return optimize.newton(Px, 0.03, maxiter=500)
Ambos me están dando resultados que no tienen sentido (como un 25% YTM).
¿Cómo puedo obtener algunos resultados significativos para estos temas tan experimentados?