在·VNPY中按照CTA策略例項記錄交易條目和損益
這個是一個常見需求,按照策略例項記錄交易條目和損益。整體的損益可以透過第三方行情軟體來分析,如果有多個CTA策略例項(策略-品種-引數組合例項),如何對每個策略例項記錄交易條目和損益情況。
下面程式碼是在vntrader 2.6 級別的例項程式碼,並不完全,因為改動比較多,這個僅僅是一個思路的示例。
先簡單介紹下思路,記錄分為3個部分,一個是新建觸發停止單物件加入觸發價,首單價和成交均價資訊,二個把完成的觸發停止單和對應的交易單儲存到資料庫,第三個根據每次offset的觸發停止單,平倉價格數量和開倉觸發停止單的開方價格數量,統計出當前的歷史平倉總收益,如果沒平倉就是當前價格的開倉收益,儲存到json或者資料庫都可以。
首先, cta_strategy/base.py 中增加一個新的event型別 EVENT_CTA_TRIGGERED_STOPORDER,用做觸發的stop order事件
EVENT_CTA_TRIGGERED_STOPORDER = 'eCtaTriggeredStopOrder'
在 cta_strategy/ engine.py 中,在方法 check_stop_order加入下面程式碼, 這個程式碼是建立一個新的物件triggered_stop_order,是一個觸發的stop order, 加入已成交筆數,觸發價,首單價和成交均價資訊。
# Update stop order status if placed successfully if vt_orderids: # Remove from relation map. if vt_orderids == 1: self.write_log(f"取消掛單,{strategy.strategy_name} {stop_order.stop_orderid}") self.cancel_order(strategy,stop_order.stop_orderid) return self.stop_orders.pop(stop_order.stop_orderid) strategy_vt_orderids = self.strategy_orderid_map[strategy.strategy_name] if stop_order.stop_orderid in strategy_vt_orderids: strategy_vt_orderids.remove(stop_order.stop_orderid) # Change stop order status to cancelled and update to strategy. stop_order.status = StopOrderStatus.TRIGGERED stop_order.vt_orderids = vt_orderids # Billy add to triggerred_stop_order dict triggered_stop_order = copy(stop_order) # triggered_stop_order.vt_orderids = list(map(lambda name: name.split(".")[1], triggered_stop_order.vt_orderids)) triggered_stop_order.stop_orderid = triggered_stop_order.stop_orderid + "." + stop_order.strategy_name + "." + '.'.join( vt_orderids) triggered_stop_order.datetime = copy(tick.datetime) triggered_stop_order.completed_volume = 0 triggered_stop_order.average_price = 0 triggered_stop_order.first_price = 0 triggered_stop_order.triggered_price = tick.last_price for vt_orderid in vt_orderids: self.vt_orderid_triggered_stop_order[vt_orderid] = triggered_stop_order # end Billy add self.call_strategy_func( strategy, strategy.on_stop_order, stop_order ) self.put_stop_order_event(stop_order)
在方法process_trade_event, 加入下面程式碼,這段程式碼是根據在triggered_stop_order中記錄的真實交易單號,如果返回的交易資訊屬於這個triggered_stop_order,那麼記錄成交數量,成交價格,算出平均價格,並且把這個trade資訊儲存到資料。這個儲存時候把 triggered_stop_order的id放到 trade裡面,方便日後關聯
如果搜到的真實交易單的累計筆數和掛單筆數一致,說明掛單已經完成狀態,把 triggered_stop_order放入資料庫。
# Update strategy pos before calling on_trade method if trade.direction == Direction.LONG: strategy.pos += trade.volume else: strategy.pos -= trade.volume self.call_strategy_func(strategy, strategy.on_trade, trade) # Billy added, update triggered_stop_order cta_trade = copy(trade) allComplete = False if cta_trade.vt_orderid in self.vt_orderid_triggered_stop_order.keys(): triggered_stop_order = self.vt_orderid_triggered_stop_order[cta_trade.vt_orderid] if triggered_stop_order.first_price == 0: triggered_stop_order.first_price = cta_trade.price triggered_stop_order.completed_volume += cta_trade.volume triggered_stop_order.average_price += cta_trade.volume * cta_trade.price # change orderid to stop_orderid cta_trade.orderid = triggered_stop_order.stop_orderid # current_triggered_stop_order = triggered_stop_order if triggered_stop_order.completed_volume == triggered_stop_order.volume: allComplete = True self.call_strategy_func(strategy, strategy.on_cta_trade, cta_trade) if allComplete: # Sync strategy variables to data file self.sync_strategy_data(strategy) triggered_stop_order.average_price = round( triggered_stop_order.average_price / triggered_stop_order.completed_volume, 2) self.put_cta_triggered_stoporder_event(triggered_stop_order) database_manager.save_triggered_stop_order_data(copy(triggered_stop_order)) for k in triggered_stop_order.vt_orderids: self.vt_orderid_triggered_stop_order.pop(k) self.call_strategy_func(strategy, strategy.save_setting_file) # Update GUI self.put_strategy_event(strategy)
寫入資料庫方法這裡不做累述,這個顯示下trade和 triggered_stop_order的資料結構示例
Trade的orderidd
{ "_id" : ObjectId("628b9523134fcca9c87671ea"), "datetime" : ISODate("2022-05-23T22:07:31.000Z"), "strategy" : "oneBar", "symbol" : "rb2210", "tradeid" : " 78259", "exchange" : "SHFE", "orderid" : "STOP.4.oneBar.CTP.3_-1818434211_2", "direction" : "空", "offset" : "開", "price" : 4594.0, "volume" : 1.0, "date" : ISODate("2022-05-23T00:00:00.000Z") }
對應的triggered_stop_order,
{ "_id" : ObjectId("628b9523134fcca9c87671ec"), "datetime" : ISODate("2022-05-23T22:07:31.500Z"), "stop_orderid" : "STOP.4.oneBar.CTP.3_-1818434211_2", "strategy_name" : "oneBar", "vt_symbol" : "rb2210.SHFE", "direction" : "空", "offset" : "開", "price" : 4594.0, "volume" : 1.0, "lock" : false, "net" : false, "vt_orderids" : [ "CTP.3_-1818434211_2" ], "status" : "已觸發", "completed_volume" : 1.0, "average_price" : 4594.0, "first_price" : 4594.0, "triggered_price" : 4594.0 }
至於之後查詢很多方法,可以用第三方分析軟體,也可以簡單做個頁面。
至於損益的分析,可以 根據每次offset的觸發停止單,平倉價格數量和開倉觸發停止單的開方價格數量,統計出當前的歷史平倉總收益,如果沒平倉就是當前價格的開倉收益,儲存到json或者資料庫都可以。
這裡要注意的是移倉操作,可能對導致開平倉交易對對上。所以在移倉也要做對應的增強。具體我後面寫一下增強的移倉程式碼
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/22259926/viewspace-2916987/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- 在VNPY2的進行CTA批量回測,支援Json和Excel格式匯入策略JSONExcel
- VNPY 基於SAR和肯特納的交易策略
- VNPY中 Tick級別準高頻交易簡單策略
- 為VNPY增加資料庫記錄交易資料功能資料庫
- VNPY 交易所返回委託和交易狀態到策略的原始碼分析原始碼
- 經常性損益和非經常性損益
- 策略模式例項模式
- VNPY 自帶跨時間週期交易策略MultiTimeframeStrategy 分析
- 在VNPY中策略中,使用分鐘線合成日K線
- linux許可權管理,例項: 建立共享目錄Linux
- Oracle 例項和RAC叢集下資料庫日誌目錄合集Oracle資料庫
- C# ling to sql 取多條記錄最大時間的例項程式碼C#SQL
- VNPY 單品種期貨的網格交易策略的實現
- VNPY 一種基於統計的交易策略簡易實現
- 在 Linux 中如何歸檔檔案和目錄Linux
- 記錄幾個例項和解決方案
- JVM中java例項物件在記憶體中的佈局JVMJava物件記憶體
- 阿里雲伺服器ECS例項建立記錄阿里伺服器
- VNPY實盤交易中,出現發單成功但是沒有交易情況
- Linux中返回上一級目錄和返回根目錄命令Linux
- 記錄一次排查log4cxx庫按照日期回滾,不建立新目錄的BUG
- 在word中怎麼設定目錄 word設定目錄的方法
- VNPY 中基於Ta-lib的KDJ策略實現
- 題目記錄
- 在Windows中執行多個MySQL例項WindowsMySql
- 在例項中呼叫 Invoke 型別的類型別
- [譯]在JavaScript中建立WebAssembly模組例項JavaScriptWeb
- CSS條紋背景程式碼例項CSS
- GObject學習筆記(一)類和例項GoObject筆記
- 類和例項
- python中類的建立和例項化Python
- 筆記:Linux命令(目錄和檔案管理)筆記Linux
- VNPY 批量策略回測和統計結果的excel輸出Excel
- Linux中操作工作目錄和檔案目錄Linux
- 雜項記錄
- 在linux下顯示中文目錄和檔名Linux
- GO 筆記-目錄Go筆記
- DSBridge例項-在網頁中展示Native進度網頁