当前位置:网站首页>Back test of quantitative trading - tqzfuturerenkowavestrategy
Back test of quantitative trading - tqzfuturerenkowavestrategy
2022-06-25 12:59:00 【Post-Truth】
from math import ceil, floor
from tqz_strategy.template import CtaTemplate
from public_module.object import BarData, RenkoData
from public_module.constant import RenkoDirection
from public_module.utility import BarGenerator
"""
Divergence or Turn potential Departure
"""
class TQZFutureRenkoWaveStrategy(CtaTemplate):
"""
future strategy(1h period). abandoned
"""
author = "tqz"
# --- param part ---
fast_window = 30
slow_window = 250
lots_size = 0
renko_size = 0
min_tick_price_flow = 0
parameters = ["fast_window", "slow_window", "lots_size", "renko_size", "min_tick_price_flow"]
# --- var part ---
fast_ma_value = 0.0
slow_ma_value = 0.0
variables = ["fast_ma_value", "slow_ma_value"]
def __init__(self, cta_engine, strategy_name, vt_symbol, setting):
""""""
super().__init__(cta_engine, strategy_name, vt_symbol, setting)
self.bg = BarGenerator(self.on_bar)
self.bar_close_prices = []
self.renko_list = []
self.high_renko_prices = []
self.low_renko_prices = []
self.first_bar_close_price = 0
def on_bar(self, bar: BarData):
"""
Callback of new bar data update.
"""
# 1. update self.bars_close_prices & update params.
if self.__update_params_ok(new_bar=bar) is False:
return
# 2. trend direction.
long_direction = self.fast_ma_value > self.slow_ma_value
short_direction = self.fast_ma_value < self.slow_ma_value
# 3. modify postion.
last_renko0 = self.renko_list[-1]
last_renko1 = self.renko_list[-2]
if long_direction:
if self.pos == 0:
if last_renko1.renko_direction == RenkoDirection.SHORT and last_renko0.renko_direction == RenkoDirection.LONG:
self.set_position(pos=self.lots_size)
elif self.pos < 0:
if last_renko1.renko_direction == RenkoDirection.SHORT and last_renko0.renko_direction == RenkoDirection.LONG:
self.set_position(pos=self.lots_size)
else:
self.set_position(pos=0)
elif self.pos > 0:
if last_renko1.renko_direction == RenkoDirection.LONG and last_renko0.renko_direction == RenkoDirection.SHORT:
if len(self.high_renko_prices) >= 2:
if self.high_renko_prices[-1] < self.high_renko_prices[-2]:
self.set_position(pos=0)
elif short_direction:
if self.pos == 0:
if last_renko1.renko_direction == RenkoDirection.LONG and last_renko0.renko_direction == RenkoDirection.SHORT:
self.set_position(pos=-1 * self.lots_size)
elif self.pos > 0:
if last_renko1.renko_direction == RenkoDirection.LONG and last_renko0.renko_direction == RenkoDirection.SHORT:
self.set_position(pos=-1 * self.lots_size)
else:
self.set_position(pos=0)
elif self.pos < 0:
if last_renko1.renko_direction == RenkoDirection.SHORT and last_renko0.renko_direction == RenkoDirection.LONG:
if len(self.low_renko_prices) >= 2:
if self.low_renko_prices[-1] > self.low_renko_prices[-2]:
self.set_position(pos=0)
def __update_params_ok(self, new_bar: BarData) -> bool:
if len(self.bar_close_prices) < self.slow_window:
self.bar_close_prices.append(new_bar.close_price)
self.__update_renko_list(new_bar=new_bar)
return False
# update self.bar_close_prices
self.bar_close_prices.remove(self.bar_close_prices[0])
self.bar_close_prices.append(new_bar.close_price)
# update fast_ma & slow_ma
self.fast_ma_value = sum(self.bar_close_prices[-self.fast_window:]) / self.fast_window
self.slow_ma_value = sum(self.bar_close_prices[-self.slow_window:]) / self.slow_window
# update renko_list
self.__update_renko_list(new_bar=new_bar)
return True
def __update_renko_list(self, new_bar: BarData):
if len(self.renko_list) is 0:
if self.first_bar_close_price is 0: # init strategy.
self.first_bar_close_price = new_bar.close_price
else:
""" Determine whether the generation of the first renko Conditions """
ticks_diff = (new_bar.close_price - self.first_bar_close_price) / self.min_tick_price_flow
if ticks_diff > self.renko_size:
""" Update the first renko In red """
renko_counts = floor(ticks_diff / self.renko_size)
renko_price = self.first_bar_close_price + renko_counts * self.renko_size * self.min_tick_price_flow
self.renko_list.append(RenkoData(renko_price=renko_price, renko_direction=RenkoDirection.LONG, renko_value=renko_counts))
elif ticks_diff < -1 * self.renko_size:
""" Update the first renko It's green """
renko_counts = ceil(ticks_diff / self.renko_size)
renko_price = self.first_bar_close_price + renko_counts * self.renko_size * self.min_tick_price_flow
self.renko_list.append(RenkoData(renko_price=renko_price, renko_direction=RenkoDirection.SHORT, renko_value=renko_counts))
else:
last_renko = self.renko_list[-1]
ticks_diff = (new_bar.close_price - last_renko.renko_price) / self.min_tick_price_flow
if last_renko.renko_direction == RenkoDirection.LONG: # Currently, it is red brick
if ticks_diff > self.renko_size:
""" Add red bricks """
renko_counts = floor(ticks_diff / self.renko_size)
renko_price = last_renko.renko_price + renko_counts * self.renko_size * self.min_tick_price_flow
self.renko_list.append(RenkoData(renko_price=renko_price, renko_direction=RenkoDirection.LONG, renko_value=last_renko.renko_value+renko_counts))
elif ticks_diff < -2 * self.renko_size:
""" New green brick """
renko_counts = ceil(ticks_diff / self.renko_size)
renko_price = last_renko.renko_price + renko_counts * self.renko_size * self.min_tick_price_flow
self.renko_list.append(RenkoData(renko_price=renko_price, renko_direction=RenkoDirection.SHORT, renko_value=renko_counts+1))
if self.pos > 0:
self.high_renko_prices.append(renko_price)
elif last_renko.renko_direction == RenkoDirection.SHORT: # Currently green bricks
if ticks_diff < -1 * self.renko_size:
""" New green brick """
renko_counts = ceil(ticks_diff / self.renko_size)
renko_price = last_renko.renko_price + renko_counts * self.renko_size * self.min_tick_price_flow
self.renko_list.append(RenkoData(renko_price=renko_price, renko_direction=RenkoDirection.SHORT, renko_value=last_renko.renko_value+renko_counts))
elif ticks_diff > 2 * self.renko_size:
""" Add red bricks """
renko_counts = floor(ticks_diff / self.renko_size)
renko_price = last_renko.renko_price + renko_counts * self.renko_size * self.min_tick_price_flow
self.renko_list.append(RenkoData(renko_price=renko_price, renko_direction=RenkoDirection.LONG, renko_value=renko_counts-1))
if self.pos < 0:
self.low_renko_prices.append(renko_price)
def set_position(self, pos: int):
if (self.pos > 0 and pos < 0) or (self.pos < 0 and pos > 0) or (pos is 0):
self.high_renko_prices = []
self.low_renko_prices = []
self.pos = pos
def on_init(self):
"""
Callback when strategy is inited.
"""
self.write_log(msg=f'strategy_name: {self.strategy_name}, fast_window: {self.fast_window}, slow_window: {self.slow_window}, lots_size: {self.lots_size}, renko_size: {self.renko_size}, min_tick_price_flow: {self.min_tick_price_flow} on_init.')
pass
def on_start(self):
"""
Callback when strategy is started.
"""
self.write_log(msg=f'strategy_name: {self.strategy_name} on_start.')
pass
def on_stop(self):
"""
Callback when strategy is stopped.
"""
self.write_log(msg=f'strategy_name: {self.strategy_name} on_stop.')
边栏推荐
- 2021-09-30
- Connect with the flight book and obtain the user information according to the userid
- The amount is verified, and two zeros are spliced by integers during echo
- Methods of strings in JS charat(), charcodeat(), fromcharcode(), concat(), indexof(), split(), slice(), substring()
- Jupyter notebook theme font setting and automatic code completion
- [Visio]平行四边形在Word中模糊问题解决
- Why are databases cloud native?
- 汇编标志位相关知识点(连)
- Serevlt初识
- KDD 2022 | GraphMAE:自监督掩码图自编码器
猜你喜欢
20220620 面试复盘
Why are databases cloud native?
剑指Offer 第 2 天链表(简单)
It is extraordinary to make a move, which is very Oracle!
The drop-down box renders numbers instead of the corresponding text. How to deal with it
AI assisted paper drawing of PPT drawing
剑指 Offer II 032. 有效的变位词
[flask tutorial] flask overview
J2EE从入门到入土01.MySQL安装
PPT绘论文图之导出分辨率
随机推荐
mysql导入导出数据到excel表日期出现问题
百度搜索稳定性问题分析的故事
list. replace, str.append
Jupyter notebook theme font setting and automatic code completion
Resolved: could not find artifact XXX
重装cuda/cudnn/pytorch
Slice() and slice() methods of arrays in JS
Online service emergency research methodology
模块五(微博评论)
用include what you use拯救混乱的头文件
Geospatial search: implementation principle of KD tree
Common colors for drawing
英语口语 - 弱读
Oral English - continuous reading
量化交易之回测篇 - 期货CTA策略实例(TQZFutureRenkoScalpingStrategy)
浏览器的5种观察器
KVM 脚本管理 —— 筑梦之路
Reload cuda/cudnn/pytorch
出手即不凡,这很 Oracle!
Sword finger offer day 1 stack and queue (simple)