From f2787e2390d6c791aae45c352f93c19a9a2c3361 Mon Sep 17 00:00:00 2001 From: "vn.py" Date: Wed, 21 Mar 2018 12:35:25 +0800 Subject: [PATCH] =?UTF-8?q?[Add]=E6=96=B0=E5=A2=9EcrrCython=E6=9C=9F?= =?UTF-8?q?=E6=9D=83=E5=AE=9A=E4=BB=B7=E6=A8=A1=E5=9E=8B=EF=BC=8C=E6=84=9F?= =?UTF-8?q?=E8=B0=A2=E6=9D=AD=E5=B7=9E-Michael=E7=9A=84=E8=B4=A1=E7=8C=AE?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- vnpy/pricing/bsCython/bsCython.pyx | 2 + vnpy/pricing/crr.py | 8 +- vnpy/pricing/crrCython.pyd | Bin 0 -> 58880 bytes vnpy/pricing/crrCython/crrCython.pyx | 158 +++++++++++++++++++++++ vnpy/pricing/crrCython/setup.py | 11 ++ vnpy/trader/app/optionMaster/omEngine.py | 3 +- 6 files changed, 178 insertions(+), 4 deletions(-) create mode 100644 vnpy/pricing/crrCython.pyd create mode 100644 vnpy/pricing/crrCython/crrCython.pyx create mode 100644 vnpy/pricing/crrCython/setup.py diff --git a/vnpy/pricing/bsCython/bsCython.pyx b/vnpy/pricing/bsCython/bsCython.pyx index b6c5be1f..5cfff6ab 100644 --- a/vnpy/pricing/bsCython/bsCython.pyx +++ b/vnpy/pricing/bsCython/bsCython.pyx @@ -1,3 +1,5 @@ +from __future__ import division + DX_TARGET = 0.00001 diff --git a/vnpy/pricing/crr.py b/vnpy/pricing/crr.py index 6d70ec52..ca7fabcd 100644 --- a/vnpy/pricing/crr.py +++ b/vnpy/pricing/crr.py @@ -1,5 +1,7 @@ # encoding: UTF-8 +from __future__ import division + ''' Cox-Ross-Rubinstein二叉树期权定价模型,主要用于标的物为期货的美式期权的定价 @@ -54,7 +56,7 @@ def generateTree(f, k, r, t, v, cp, n): p = (a - d) / (u - d) p1 = p / a p2 = (1 - p) / a - + # 计算标的树 uTree[0, 0] = f @@ -139,9 +141,9 @@ def calculateImpv(price, f, k, r, t, cp, n=15): # 检查期权价格是否满足最小价值(即到期行权价值) meet = False - if cp == 1 and (price > f - k): + if cp == 1 and price > (f - k): meet = True - elif cp == -1 and (price > k - f): + elif cp == -1 and price > (k - f): meet = True # 若不满足最小价值,则直接返回0 diff --git a/vnpy/pricing/crrCython.pyd b/vnpy/pricing/crrCython.pyd new file mode 100644 index 0000000000000000000000000000000000000000..60979cdbbe7a6bb0aa9267d8533dccfc1c6c8ef4 GIT binary patch literal 58880 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 EzadbG (f - k): + meet = True + elif cp == -1 and price > (k - f): + meet = True + + if not meet: + return 0 + + v = 0.3 + + try: + for i in range(50): + p = calculatePrice(f, k, r, t, v, cp, n) + vega = calculateOriginalVega(f, k, r, t, v, cp, n) + + if not vega: + break + + dx = (price - p) / vega + if abs(dx) < DX_TARGET: + break + + v += dx + except: + v = 0 + + if v <= 0: + return 0 + + v = round(v, 4) + return v \ No newline at end of file diff --git a/vnpy/pricing/crrCython/setup.py b/vnpy/pricing/crrCython/setup.py new file mode 100644 index 00000000..982874d7 --- /dev/null +++ b/vnpy/pricing/crrCython/setup.py @@ -0,0 +1,11 @@ +# encoding: UTF-8 +from distutils.core import setup +from Cython.Build import cythonize +import numpy + + +setup( + name = 'crrCython', + ext_modules = cythonize("crrCython.pyx"), + include_dirs = [numpy.get_include()] +) diff --git a/vnpy/trader/app/optionMaster/omEngine.py b/vnpy/trader/app/optionMaster/omEngine.py index 8f9a5e8e..044ac7c0 100644 --- a/vnpy/trader/app/optionMaster/omEngine.py +++ b/vnpy/trader/app/optionMaster/omEngine.py @@ -17,7 +17,7 @@ from vnpy.trader.vtConstant import (PRODUCT_OPTION, OPTION_CALL, OPTION_PUT, DIRECTION_LONG, DIRECTION_SHORT, OFFSET_OPEN, OFFSET_CLOSE, PRICETYPE_LIMITPRICE) -from vnpy.pricing import black, bs, crr, bsCython +from vnpy.pricing import black, bs, crr, bsCython, crrCython from .omBase import (OmOption, OmUnderlying, OmChain, OmPortfolio, EVENT_OM_LOG, EVENT_OM_STRATEGY, EVENT_OM_STRATEGYLOG, @@ -32,6 +32,7 @@ MODEL_DICT['black'] = black MODEL_DICT['bs'] = bs MODEL_DICT['crr'] = crr MODEL_DICT['bsCython'] = bsCython +MODEL_DICT['crrCython'] = crrCython