diff options
| -rw-r--r-- | pyisda/credit_index.pyx | 38 |
1 files changed, 29 insertions, 9 deletions
diff --git a/pyisda/credit_index.pyx b/pyisda/credit_index.pyx index 4a83090..bde51d1 100644 --- a/pyisda/credit_index.pyx +++ b/pyisda/credit_index.pyx @@ -636,6 +636,11 @@ cdef class CreditIndex(CurveList): if schedule is None: schedule_ptr = self._maturities.const_data() n[1] = self._maturities.size() + if self._maturities.back() < self.base_date: + raise ValueError("matured index") + while deref(schedule_ptr) < self.base_date: + preinc(schedule_ptr) + n[1] -=1 else: schedule_ptr = &schedule[0] n[1] = schedule.shape[0] @@ -671,14 +676,15 @@ cdef class CreditIndex(CurveList): get_TCurve(yc), sc.get(), self.recovery_rates[p.second].get(), - &spreads_view[p.second, 0]) + &spreads_view[j, 0]) + j += 1 return spreads def dispersion(self, YieldCurve yc not None, const TDate[::1] schedule=None, const bint use_log=True): cdef: shared_ptr[TCurve] sc pair[CurveName, size_t] p - np.npy_intp n + np.npy_intp n, orig_size const TDate* schedule_ptr size_t i @@ -688,14 +694,17 @@ cdef class CreditIndex(CurveList): else: schedule_ptr = &schedule[0] n = schedule.shape[0] + orig_size = n + while deref(schedule_ptr) < self.base_date: + preinc(schedule_ptr) + n -= 1 cdef: - np.ndarray std_spreads = np.PyArray_ZEROS(1, &n, np.NPY_DOUBLE, 0) - double[::1] std_spreads_view = std_spreads TStubMethod stub_type double Mk, w - double* spreads = <double*>malloc(n * sizeof(double)) double* M = <double*>malloc(n * sizeof(double)) + double* spreads = <double*>malloc(n * sizeof(double)) + double* std_spreads = <double*>malloc( n * sizeof(double)) double w_sum, w_sum2 bint first_time = True @@ -740,19 +749,30 @@ cdef class CreditIndex(CurveList): for i in range(n): S = log(spreads[i]) Mk = M[i] + (w / w_sum) * (S - M[i]) - std_spreads_view[i] += w * (S - M[i]) * (S - Mk) + std_spreads[i] += w * (S - M[i]) * (S - Mk) M[i] = Mk else: for i in range(n): S = spreads[i] Mk = M[i] + (w / w_sum) * (S - M[i]) - std_spreads_view[i] += w * (S - M[i]) * (S - Mk) + std_spreads[i] += w * (S - M[i]) * (S - Mk) M[i] = Mk for i in range(n): - std_spreads_view[i] /= (w_sum - w_sum2 / w_sum) + std_spreads[i] /= (w_sum - w_sum2 / w_sum) free(M) free(spreads) - return std_spreads + + cdef: + np.ndarray r = np.PyArray_ZEROS(1, &orig_size, np.NPY_DOUBLE, 0) + double[::1] r_view = r + + for i in range(orig_size): + if i < orig_size - n: + r_view[i] = nan("") + else: + r_view[i] = std_spreads[i - orig_size + n] + free(std_spreads) + return r cdef unsigned long fill_mask(const TDate maturity, const vector[TDate]& maturities, const shared_ptr[TCurve]& sc) nogil: |
