From f1bed268cfd976966b6bab376a59c52dfd0216fa Mon Sep 17 00:00:00 2001 From: Guillaume Horel Date: Thu, 30 Jun 2016 15:02:10 -0400 Subject: rename zerocurve to curve, and merge yearfrac with date --- cdsone.pxd | 2 +- cdsone.pyx | 7 +++-- curve.pxd | 33 +++++++++++++++++++++++ curve.pyx | 84 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ date.pxd | 5 ++++ date.pyx | 12 ++++++++- yearfrac.pxd | 4 --- yearfrac.pyx | 11 -------- zerocurve.pxd | 33 ----------------------- zerocurve.pyx | 84 ----------------------------------------------------------- 10 files changed, 137 insertions(+), 138 deletions(-) create mode 100644 curve.pxd create mode 100644 curve.pyx delete mode 100644 yearfrac.pxd delete mode 100644 yearfrac.pyx delete mode 100644 zerocurve.pxd delete mode 100644 zerocurve.pyx diff --git a/cdsone.pxd b/cdsone.pxd index 0f76c50..b24d3b4 100644 --- a/cdsone.pxd +++ b/cdsone.pxd @@ -1,5 +1,5 @@ from date cimport TDateInterval -from pyisda.zerocurve cimport TCurve +from curve cimport TCurve cdef extern from "isda/stub.h": ctypedef struct TStubMethod: diff --git a/cdsone.pyx b/cdsone.pyx index cb567f6..d6bb4ec 100644 --- a/cdsone.pyx +++ b/cdsone.pyx @@ -1,8 +1,7 @@ -from pyisda.cdsone cimport (JpmcdsCdsoneUpfrontCharge, +from cdsone cimport (JpmcdsCdsoneUpfrontCharge, JpmcdsCdsoneSpread, JpmcdsStringToStubMethod) -from pyisda.zerocurve cimport ZeroCurve -from pyisda.date cimport JpmcdsStringToDateInterval, pydate_to_TDate -from pyisda.yearfrac cimport dcc +from curve cimport ZeroCurve +from date cimport JpmcdsStringToDateInterval, pydate_to_TDate, dcc cdef int SUCCESS = 0 diff --git a/curve.pxd b/curve.pxd new file mode 100644 index 0000000..d652ca0 --- /dev/null +++ b/curve.pxd @@ -0,0 +1,33 @@ +cdef extern from "isda/zerocurve.h": + + ctypedef long int TDate + + ctypedef struct TCurve: + pass + + ctypedef struct TDateInterval: + pass + + TCurve* JpmcdsBuildIRZeroCurve(TDate valueDate, + char* instrNames, + TDate* dates, + double* rates, + long nInstr, + long mmDCC, + long fixedSwapFreq, + long floatSwapFreq, + long fixedSwapDCC, + long floatSwapDCC, + long badDayConv, + char* holidayFile) + +cdef extern from "isda/tcurve.h": + void JpmcdsFreeTCurve(TCurve* curve) + +cdef extern from "isda/cxzerocurve.h": + double JpmcdsZeroPrice(TCurve* curve, TDate date) + +cdef class ZeroCurve: + cdef TCurve* _thisptr + cdef TDate* _dates + cdef size_t _ninstr diff --git a/curve.pyx b/curve.pyx new file mode 100644 index 0000000..a5eb2d2 --- /dev/null +++ b/curve.pyx @@ -0,0 +1,84 @@ +from cpython cimport datetime +from libc.stdlib cimport malloc, free +from pyisda.zerocurve cimport JpmcdsBuildIRZeroCurve, JpmcdsZeroPrice +from pyisda.yearfrac cimport dcc +from pyisda.date cimport (JpmcdsStringToDateInterval, pydate_to_TDate, + JpmcdsDateIntervalToFreq, JpmcdsDateFwdThenAdjust, TDate_to_pydate, + JpmcdsDateFromBusDaysOffset) + +cdef int SUCCESS = 0 + +cpdef public enum BadDay: + FOLLOW = 'F' + PREVIOUS = 'P' + NONE = 'N' + MODIFIED = 'M' + +cdef class ZeroCurve: + + def __init__(self, date, str types, + list periods, double[:] rates, + str mm_dcc, str fixed_swap_period, str float_swap_period, + str fixed_swap_dcc, str float_swap_dcc, BadDay bad_day_conv): + """ Initialize a zero coupon curve + + instruments need to be sorted by tenor + """ + cdef: + double fixed_freq + double float_freq + TDateInterval ivl + char* routine = 'zerocurve' + TDate value_date = pydate_to_TDate(date) + + self._dates = malloc(len(periods) * sizeof(TDate)) + self._ninstr = len(periods) + + cdef TDate settle_date + if JpmcdsDateFromBusDaysOffset(value_date, 2, "None", &settle_date)!= SUCCESS: + raise ValueError + + cdef TDateInterval tmp + for i, p in enumerate(periods): + period_bytes = p.encode('utf-8') + if JpmcdsStringToDateInterval(period_bytes, routine, &tmp) != SUCCESS: + raise ValueError + if JpmcdsDateFwdThenAdjust(settle_date, &tmp, NONE, + "None", &self._dates[i]) != SUCCESS: + raise ValueError('Invalid interval') + + fixed_bytes = fixed_swap_period.encode('utf-8') + float_bytes = float_swap_period.encode('utf-8') + types_bytes = types.encode('utf-8') + + if JpmcdsStringToDateInterval(fixed_bytes, routine, &ivl) != SUCCESS: + raise ValueError + if JpmcdsDateIntervalToFreq(&ivl, &fixed_freq) != SUCCESS: + raise ValueError + if JpmcdsStringToDateInterval(float_bytes, routine, &ivl) != SUCCESS: + raise ValueError + if JpmcdsDateIntervalToFreq(&ivl, &float_freq) != SUCCESS: + raise ValueError + + self._thisptr = JpmcdsBuildIRZeroCurve( + value_date, types_bytes, self._dates, + &rates[0], len(periods), dcc(mm_dcc), fixed_freq, + float_freq, dcc(fixed_swap_dcc), dcc(float_swap_dcc), + bad_day_conv, b"None" + ) + + def __dealloc__(self): + if self._thisptr is not NULL: + JpmcdsFreeTCurve(self._thisptr) + if self._dates is not NULL: + free(self._dates) + + def discount_factor(self, date): + if self._thisptr is NULL: + raise ValueError('curve is empty') + cdef TDate discount_date = pydate_to_TDate(date) + return JpmcdsZeroPrice(self._thisptr, discount_date) + + def list_dates(self): + cdef size_t i + return [TDate_to_pydate(self._dates[i]) for i in range(self._ninstr)] diff --git a/date.pxd b/date.pxd index 16b2261..a10d922 100644 --- a/date.pxd +++ b/date.pxd @@ -1,3 +1,8 @@ +cdef extern from "isda/yearfrac.h": + int JpmcdsStringToDayCountConv(char* day_count, long* type) + +cdef long dcc(str day_count) + cdef extern from "isda/cdate.h": ctypedef struct TDateInterval: pass diff --git a/date.pyx b/date.pyx index 8df0df8..26d7339 100644 --- a/date.pyx +++ b/date.pyx @@ -1,5 +1,5 @@ import datetime -from date cimport JpmcdsDate +from date cimport JpmcdsDate, JpmcdsStringToDayCountConv cdef TDate pydate_to_TDate(d): assert isinstance(d, datetime.date) @@ -9,3 +9,13 @@ cpdef object TDate_to_pydate(TDate d): cdef TMonthDayYear date if JpmcdsDateToMDY(d, &date) == 0: return datetime.date(date.year, date.month, date.day) + +cdef long dcc(str day_count): + cdef long r + dc_bytes = day_count.encode('utf-8') + cdef char* dc = dc_bytes + cdef err = JpmcdsStringToDayCountConv( dc, &r) + if err == 0: + return r + else: + raise ValueError('{0} is not a valid day count'.format(day_count)) diff --git a/yearfrac.pxd b/yearfrac.pxd deleted file mode 100644 index 739ca90..0000000 --- a/yearfrac.pxd +++ /dev/null @@ -1,4 +0,0 @@ -cdef extern from "isda/yearfrac.h": - int JpmcdsStringToDayCountConv(char* day_count, long* type) - -cdef long dcc(str day_count) diff --git a/yearfrac.pyx b/yearfrac.pyx deleted file mode 100644 index 48b8995..0000000 --- a/yearfrac.pyx +++ /dev/null @@ -1,11 +0,0 @@ -from pyisda.yearfrac cimport JpmcdsStringToDayCountConv - -cdef long dcc(str day_count): - cdef long r - dc_bytes = day_count.encode('utf-8') - cdef char* dc = dc_bytes - cdef err = JpmcdsStringToDayCountConv( dc, &r) - if err == 0: - return r - else: - raise ValueError('{0} is not a valid day count'.format(day_count)) diff --git a/zerocurve.pxd b/zerocurve.pxd deleted file mode 100644 index d652ca0..0000000 --- a/zerocurve.pxd +++ /dev/null @@ -1,33 +0,0 @@ -cdef extern from "isda/zerocurve.h": - - ctypedef long int TDate - - ctypedef struct TCurve: - pass - - ctypedef struct TDateInterval: - pass - - TCurve* JpmcdsBuildIRZeroCurve(TDate valueDate, - char* instrNames, - TDate* dates, - double* rates, - long nInstr, - long mmDCC, - long fixedSwapFreq, - long floatSwapFreq, - long fixedSwapDCC, - long floatSwapDCC, - long badDayConv, - char* holidayFile) - -cdef extern from "isda/tcurve.h": - void JpmcdsFreeTCurve(TCurve* curve) - -cdef extern from "isda/cxzerocurve.h": - double JpmcdsZeroPrice(TCurve* curve, TDate date) - -cdef class ZeroCurve: - cdef TCurve* _thisptr - cdef TDate* _dates - cdef size_t _ninstr diff --git a/zerocurve.pyx b/zerocurve.pyx deleted file mode 100644 index a5eb2d2..0000000 --- a/zerocurve.pyx +++ /dev/null @@ -1,84 +0,0 @@ -from cpython cimport datetime -from libc.stdlib cimport malloc, free -from pyisda.zerocurve cimport JpmcdsBuildIRZeroCurve, JpmcdsZeroPrice -from pyisda.yearfrac cimport dcc -from pyisda.date cimport (JpmcdsStringToDateInterval, pydate_to_TDate, - JpmcdsDateIntervalToFreq, JpmcdsDateFwdThenAdjust, TDate_to_pydate, - JpmcdsDateFromBusDaysOffset) - -cdef int SUCCESS = 0 - -cpdef public enum BadDay: - FOLLOW = 'F' - PREVIOUS = 'P' - NONE = 'N' - MODIFIED = 'M' - -cdef class ZeroCurve: - - def __init__(self, date, str types, - list periods, double[:] rates, - str mm_dcc, str fixed_swap_period, str float_swap_period, - str fixed_swap_dcc, str float_swap_dcc, BadDay bad_day_conv): - """ Initialize a zero coupon curve - - instruments need to be sorted by tenor - """ - cdef: - double fixed_freq - double float_freq - TDateInterval ivl - char* routine = 'zerocurve' - TDate value_date = pydate_to_TDate(date) - - self._dates = malloc(len(periods) * sizeof(TDate)) - self._ninstr = len(periods) - - cdef TDate settle_date - if JpmcdsDateFromBusDaysOffset(value_date, 2, "None", &settle_date)!= SUCCESS: - raise ValueError - - cdef TDateInterval tmp - for i, p in enumerate(periods): - period_bytes = p.encode('utf-8') - if JpmcdsStringToDateInterval(period_bytes, routine, &tmp) != SUCCESS: - raise ValueError - if JpmcdsDateFwdThenAdjust(settle_date, &tmp, NONE, - "None", &self._dates[i]) != SUCCESS: - raise ValueError('Invalid interval') - - fixed_bytes = fixed_swap_period.encode('utf-8') - float_bytes = float_swap_period.encode('utf-8') - types_bytes = types.encode('utf-8') - - if JpmcdsStringToDateInterval(fixed_bytes, routine, &ivl) != SUCCESS: - raise ValueError - if JpmcdsDateIntervalToFreq(&ivl, &fixed_freq) != SUCCESS: - raise ValueError - if JpmcdsStringToDateInterval(float_bytes, routine, &ivl) != SUCCESS: - raise ValueError - if JpmcdsDateIntervalToFreq(&ivl, &float_freq) != SUCCESS: - raise ValueError - - self._thisptr = JpmcdsBuildIRZeroCurve( - value_date, types_bytes, self._dates, - &rates[0], len(periods), dcc(mm_dcc), fixed_freq, - float_freq, dcc(fixed_swap_dcc), dcc(float_swap_dcc), - bad_day_conv, b"None" - ) - - def __dealloc__(self): - if self._thisptr is not NULL: - JpmcdsFreeTCurve(self._thisptr) - if self._dates is not NULL: - free(self._dates) - - def discount_factor(self, date): - if self._thisptr is NULL: - raise ValueError('curve is empty') - cdef TDate discount_date = pydate_to_TDate(date) - return JpmcdsZeroPrice(self._thisptr, discount_date) - - def list_dates(self): - cdef size_t i - return [TDate_to_pydate(self._dates[i]) for i in range(self._ninstr)] -- cgit v1.2.3-70-g09d2