summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--pyisda/curve.pxd12
-rw-r--r--pyisda/curve.pyx65
2 files changed, 77 insertions, 0 deletions
diff --git a/pyisda/curve.pxd b/pyisda/curve.pxd
index 61d55de..b30ffe1 100644
--- a/pyisda/curve.pxd
+++ b/pyisda/curve.pxd
@@ -1,4 +1,5 @@
from cdsone cimport TStubMethod
+from legs cimport TContingentLeg, TFeeLeg
cdef extern from "isda/zerocurve.h" nogil:
ctypedef int TBoolean
@@ -85,6 +86,10 @@ cdef extern from "isda/tcurve.h" nogil:
long dayCountConv)
TCurve* JpmcdsCopyCurve(TCurve* curve)
TDate* JpmcdsDatesFromCurve(TCurve* curve)
+ TCurve* JpmcdsNewTCurve(TDate baseDate, # (I) Base date
+ int numPts, # (I) Length of dates & rates
+ double basis, # (I) Compounding periods/year
+ long dayCountConv)
cdef extern from "isda/cxzerocurve.h" nogil:
double JpmcdsZeroPrice(TCurve* curve, TDate date)
@@ -112,4 +117,11 @@ cdef class YieldCurve(Curve):
cdef class SpreadCurve(Curve):
pass
+cdef class BasketIndex:
+ cdef TCurve* _sc
+ cdef TContingentLeg* _contingent_leg
+ cdef TFeeLeg* _fee_leg
+ cdef double* _T
+ cdef double[:,::1] _rate
+
cdef fArray_to_list(TRatePt* fArray, int fNumItems)
diff --git a/pyisda/curve.pyx b/pyisda/curve.pyx
index 15f48a5..e481c22 100644
--- a/pyisda/curve.pyx
+++ b/pyisda/curve.pyx
@@ -6,6 +6,9 @@ from date cimport (JpmcdsStringToDateInterval, pydate_to_TDate, dcc,
JpmcdsDateFromBusDaysOffset, JpmcdsStringToDayCountConv)
from date import dcc_tostring
from cdsone cimport JpmcdsStringToStubMethod, TStubMethod
+from legs cimport (JpmcdsCdsContingentLegMake, JpmcdsCdsFeeLegMake,
+ JpmcdsContingentLegPV, JpmcdsFeeLegPV)
+
cimport cython
cimport numpy as np
np.import_array()
@@ -431,3 +434,65 @@ cdef class SpreadCurve(Curve):
return self
else:
return sc
+
+cdef class BasketIndex:
+ def __init__(self, base_date, start_date, end_date,
+ list end_dates, double[:,::1] hazard_rates):
+ cdef int n_dates = len(end_dates)
+ if n_dates != hazard_rates.shape[1]:
+ raise ValueError("Number of dates must equal the number of columns in rates")
+ cdef TDate base_date_c = pydate_to_TDate(base_date)
+ cdef TDate* end_dates_c = <TDate*>malloc(n_dates * sizeof(TDate))
+ cdef TDate start_date_c = pydate_to_TDate(start_date)
+ cdef TDate end_date_c = pydate_to_TDate(end_date)
+ self._sc = JpmcdsNewTCurve(base_date_c, n_dates, 5000., 2L)
+ cdef TDate date
+ for i, d in enumerate(end_dates):
+ date = pydate_to_TDate(d)
+ self._T[i] = (date - base_date_c) / 365.
+ self._thisptr.fArray[i].fDate = date
+ self._hazard_rates[:] = hazard_rates
+ self._contingent_leg = JpmcdsCdsContingentLegMake(start_date_c,
+ end_date_c,
+ 1.,
+ True)
+ cdef TStubMethod stub_type
+ if JpmcdsStringToStubMethod(b"f/s", &stub_type) != 0:
+ raise ValueError("can't convert stub")
+
+ self._fee_leg = JpmcdsCdsFeeLegMake(start_date_c,
+ end_date_c,
+ True,
+ NULL,
+ &stub_type,
+ 1.,
+ 0.01,
+ 3, #ACT_360
+ MODIFIED,
+ b'NONE',
+ True)
+
+ def pv(self, step_in_date, value_date, YieldCurve yc, double recovery_rate):
+ cdef step_in_date_c = pydate_to_TDate(step_in_date)
+ cdef value_date_c = pydate_to_TDate(value_date)
+ cdef size_t n = self._hazard_rates.shape[0]
+ cdef double cl_pv, fl_pv
+ for i in range(n):
+ for j in range(self._thisptr.fNumItems):
+ self._thisptr.fArray[j].fRate = self._rate[i][j]
+ JpmcdsContingentLegPV(self._contingent_leg,
+ self._sc.fBaseDate,
+ value_date_c,
+ step_in_date_c,
+ yc._thisptr,
+ self._sc,
+ recovery_rate,
+ &cl_pv)
+ JpmcdsFeeLegPV(self._fee_leg,
+ self._sc.fBaseDate,
+ step_in_date_c,
+ value_date_c,
+ yc._thisptr,
+ self._sc,
+ True,
+ &fl_pv)