pyalgotrade中事件分析器的更多示例

时间:2016-05-19 07:11:42

标签: python quantitative-finance algorithmic-trading zipline pyalgotrade

我正在尝试学习如何在pyalgotrade的事件探查器中实现自定义策略。 This is the default example they give

from pyalgotrade           import eventprofiler
from pyalgotrade.technical import stats
from pyalgotrade.technical import roc
from pyalgotrade.technical import ma
from pyalgotrade.tools     import yahoofinance

#     Event inspired on an example from Ernie Chan's book:
#    'Algorithmic Trading: Winning Strategies and Their Rationale'

class BuyOnGap(eventprofiler.Predicate):
    def __init__(self, feed):
        stdDevPeriod = 90
        smaPeriod = 20
        self.__returns = {}
        self.__stdDev = {}
        self.__ma = {}
        for instrument in feed.getRegisteredInstruments():
            priceDS = feed[instrument].getAdjCloseDataSeries()
            #      Returns over the adjusted close values.
            self.__returns[instrument] = roc.RateOfChange(priceDS, 1)
            #      StdDev over those returns.
            self.__stdDev[instrument] = stats.StdDev(self.__returns[instrument], stdDevPeriod)
            #      MA over the adjusted close values.
            self.__ma[instrument] = ma.SMA(priceDS, smaPeriod)

    def __gappedDown(self, instrument, bards):
        ret = False
        if self.__stdDev[instrument][-1] != None:
            prevBar = bards[-2]
            currBar = bards[-1]
            low2OpenRet = (currBar.getAdjOpen() - prevBar.getAdjLow()) / float(prevBar.getAdjLow())
            if low2OpenRet < (self.__returns[instrument][-1] - self.__stdDev[instrument][-1]):
                ret = True
        return ret

    def __aboveSMA(self, instrument, bards):
        ret = False
        if self.__ma[instrument][-1] != None and bards[-1].getAdjOpen() > self.__ma[instrument][-1]:
            ret = True
        return ret

    def eventOccurred(self, instrument, bards):
        ret = False
        if self.__gappedDown(instrument, bards) and self.__aboveSMA(instrument, bards):
            ret = True
        return ret

def main(plot):
    instruments = ["AA", "AES", "AIG"]
    feed = yahoofinance.build_feed(instruments, 2008, 2009, ".")

    predicate = BuyOnGap(feed)
    eventProfiler = eventprofiler.Profiler(predicate, 5, 5)
    eventProfiler.run(feed, True)

    results = eventProfiler.getResults()
    print "%d events found" % (results.getEventCount())
    if plot:
        eventprofiler.plot(results)

if __name__ == "__main__":
    main(True)

enter image description here 是否有人有更多示例来源?

我试图找出 eventprofiler如何接受和使用数据,但是有很多类方法可以调用,而且我是&#39我觉得解剖它有点棘手。

我想从简单开始,只使用pricevolume。它是,一种策略是if volume > 1000 and close < 50: event == True

任何帮助将不胜感激。

P.s。:红利问题: zipline是否有类似的事件分析器?

编辑:感谢user3666197,我能够进行我想要的更改,但是我收到了这个错误:

Traceback (most recent call last):
  File "C:\Users\David\Desktop\Python\Coursera\Computational Finance\Week2\PyAlgoTrade\Bitfinex\FCT\FCT_single_event_test.py", line 43, in <module>
    main(True)
  File "C:\Users\David\Desktop\Python\Coursera\Computational Finance\Week2\PyAlgoTrade\Bitfinex\FCT\FCT_single_event_test.py", line 35, in main
    eventProfiler.run(feed, True)
  File "C:\Python27\lib\site-packages\pyalgotrade\eventprofiler.py", line 215, in run
    disp.run()
  File "C:\Python27\lib\site-packages\pyalgotrade\dispatcher.py", line 102, in run
    eof, eventsDispatched = self.__dispatch()
  File "C:\Python27\lib\site-packages\pyalgotrade\dispatcher.py", line 90, in __dispatch
    if self.__dispatchSubject(subject, smallestDateTime):
  File "C:\Python27\lib\site-packages\pyalgotrade\dispatcher.py", line 68, in __dispatchSubject
    ret = subject.dispatch() is True
  File "C:\Python27\lib\site-packages\pyalgotrade\feed\__init__.py", line 105, in dispatch
    self.__event.emit(dateTime, values)
  File "C:\Python27\lib\site-packages\pyalgotrade\observer.py", line 59, in emit
    handler(*args, **kwargs)
  File "C:\Python27\lib\site-packages\pyalgotrade\eventprofiler.py", line 172, in __onBars
    eventOccurred = self.__predicate.eventOccurred(instrument, self.__feed[instrument])
  File "C:\Python27\lib\site-packages\pyalgotrade\eventprofiler.py", line 89, in eventOccurred
    raise NotImplementedError()
NotImplementedError
[Finished in 1.9s]

我已经查看过来源&event;事件发展日期&#39;并且无法弄清楚它是什么。这是代码

from pyalgotrade import eventprofiler
from pyalgotrade.technical import stats
from pyalgotrade.technical import roc
from pyalgotrade.technical import ma
from pyalgotrade.barfeed import csvfeed

# Event inspired on an example from Ernie Chan's book:
# 'Algorithmic Trading: Winning Strategies and Their Rationale'

class single_event_strat( eventprofiler.Predicate ):
    def __init__(self,feed):
        self.__returns = {} # CLASS ATTR
        for inst in feed.getRegisteredInstruments():

            priceDS = feed[inst].getAdjCloseDataSeries() # STORE: priceDS ( a temporary representation )

            self.__returns[inst] = roc.RateOfChange( priceDS, 1 )
            # CALC:  ATTR <- Returns over the adjusted close values, consumed priceDS 
            #( could be expressed as self.__returns[inst] = roc.RateOfChange( ( feed[inst].getAdjCloseDataSeries() ), 1 ), 
            #but would be less readable

    def eventOccoured( self, instrument, aBarDS):
        if (aBarDS[-1].getVolume() > 1000 and aBarDS[-1].getClose() > 50 ):
            return True
        else: 
            return False

def main(plot):
    feed = csvfeed.GenericBarFeed(0)

    feed.addBarsFromCSV('FCT', "FCT_daily_converted.csv")

    predicate = single_event_strat(feed)
    eventProfiler = eventprofiler.Profiler(predicate, 5, 5)
    eventProfiler.run(feed, True)

    results = eventProfiler.getResults()
    print "%d events found" % (results.getEventCount())
    if plot:
        eventprofiler.plot(results)

if __name__ == "__main__":
    main(True)

2 个答案:

答案 0 :(得分:1)

Quant Prologue:

  

Many thanks to prof. Tucker BALCH, GA-TECH [GA], and his team, for QSTK-initiative以及量化金融建模的创新方法。   enter image description here

     

eventprofiler如何获取数据?

简单地说,它可以在feed eventprofiler.run( feed中同时访问完整的 , ... ) eventprofiler.Predicate - 包裹 feed ,其中包含所有Feed详情&#39;通过Class-parameter访问 .Predicate 实例,以便能够计算出策略演算所需的所有细节。 聪明,不是吗?

其余的是通过重复使用他们的类方法来完成的。

如何建立自己的?

宣布一个配备适当的 eventprofiler.Predicate 就足够了,它将被注入evenprofiler实例中:

class DavidsSTRATEGY( eventprofiler.Predicate ):
      def __init__( self, feed ):                         # mandatory .__init__
          """                                               no need for this code
                                                            left here for didactic
                                                            purposes only
                                                            to show the principle

          self.__returns = {}                                         # CLASS ATTR

          for                inst in feed.getRegisteredInstruments():
              priceDS = feed[inst].getAdjCloseDataSeries()            # STORE: priceDS ( a temporary representation )
              self.__returns[inst] = roc.RateOfChange( priceDS, 1 )   # CALC:  ATTR <- Returns over the adjusted close values, consumed priceDS ( could be expressed as self.__returns[inst] = roc.RateOfChange( ( feed[inst].getAdjCloseDataSeries() ), 1 ), but would be less readable
          """

      def eventOccurred( self, instrument, aBarDS ):       # mandatory .eventOccured
          if (   aBarDS[-1].getVolume() > 1000             # "last" Bar's Volume >
             and aBarDS[-1].getClose()  <   50             # "last" Bar's Close  <
             ):
                 return True
          else:
                 return False

剩下的就像往常一样简单:

eventProfiler = eventprofiler.Profiler( predicate = DavidsSTRATEGY( feed ), 5, 5 )
eventProfiler.run( feed, True )

Quant Epilogue:

一位细心的读者已经注意到,建议的代码不会调用.getAdjClose()方法。理由是,深度回测可能会因为非常接近的调整,在做出决策时有所偏差,而调整尚不清楚。每个专业定量分析师的公平义务是避免任何窥视未来的方法,并在需要调整的情况下仔细决定投资组合估值,如果持有时间的工具已进行调整,则在其中进行调整。相应的生命周期,或不是。

答案 1 :(得分:1)

奖金回答

虽然问题的动机是明确的,但有几个原因,为什么答案不是那么简单,因为它可能看起来。

首先,事情是如何运作的:

eventprofiler QSTK 中的 pyalgotrade 是建立在市场的 DataSeries 表示之上,外部数据通过 feed 机制输入(未存储)。

zipline 方法与众不同,其核心功能主要集中在基于事件的模拟引擎上,该引擎在每个价格的原子角色级别上运行 - {{ 1}} - tick(异步外部事件到达和本地响应处理)。

事件流处理的顺序性质对模拟的体外回溯测试具有一定的吸引力。

QUOTE - 来源QSTK的优势正相反,基于一次处理完整 - 长度eventprofiler - 表示(或某些智能迭代器重新验证或高效 DataSeries numpy - 技巧和魔法)。

这种巨大的概念差异使得很难获得类似智能+快速+高效+易于重复使用的工具,因为stride QSTK 问题是,在事件处理环境中。