From fd5d3599c714e1843b1f48d27a9680d5e4db27a0 Mon Sep 17 00:00:00 2001 From: Denis Tereshkin Date: Wed, 25 Apr 2018 10:44:01 +0700 Subject: [PATCH] IntradayBarNumber signal --- data/signal.py | 59 +++++++++++++++++++++++++++++++++++++++++-- execution/executor.py | 4 +-- solver/solver.py | 3 ++- ui/mainwindow.py | 6 +++-- ui/mainwindow.ui | 16 +++++++++++- ui/ui_mainwindow.py | 10 +++++++- 6 files changed, 89 insertions(+), 9 deletions(-) diff --git a/data/signal.py b/data/signal.py index bf5e1fa..fb8bb73 100644 --- a/data/signal.py +++ b/data/signal.py @@ -7,7 +7,6 @@ import numpy import talib from scipy.integrate.tests.test_odeint_jac import rhs - class Signal: def __init__(self): @@ -852,4 +851,60 @@ class StochasticSignal(Signal): def get_text(self): return "stoch(c, {:d})[{:d}] {:s} {:d}".format(self.period, self.shift, self.inequality_sign_str, int(self.threshold)) - \ No newline at end of file +class IntradayBarNumberSignalGenerator: + + def __init__(self, max_ibn): + self.max_ibn = max_ibn + + def generate(self): + ibn = random.randint(0, self.max_ibn) + ineq_type = random.randint(IntradayBarNumberSignal.LT, IntradayBarNumberSignal.EQ) + return IntradayBarNumberSignal(ibn, ineq_type) + + def id(self): + return 'IBN' + + +class IntradayBarNumberSignal(Signal): + + LT = 0 + GT = 1 + EQ = 2 + + def __init__(self, ibn, inequality_type): + self.ibn = ibn + self.inequality_type = inequality_type + if inequality_type == IntradayBarNumberSignal.LT: + self.inequality_sign_str = '<' + elif inequality_type == IntradayBarNumberSignal.GT: + self.inequality_sign_str = '>' + else: + self.inequality_sign_str = '==' + + def calculate(self, series): + ibn = [] + cur_date = None + for i in range(0, series.length()): + if series.get_dt(i).date() != cur_date: + cur_date = series.get_dt(i).date() + ctr = 0 + else: + ctr += 1 + ibn.append(ctr) + + result = [] + for i in ibn: + result.append(self.calc_signal(i)) + return result + + def calc_signal(self, ibn): + if self.inequality_type == IntradayBarNumberSignal.LT: + return ibn < self.ibn + elif self.inequality_type == IntradayBarNumberSignal.GT: + return ibn > self.ibn + elif self.inequality_type == IntradayBarNumberSignal.EQ: + return ibn == self.ibn + + def get_text(self): + return "ibn {:s} {:d}".format(self.inequality_sign_str, self.ibn) + diff --git a/execution/executor.py b/execution/executor.py index d2f67ca..7d5502b 100644 --- a/execution/executor.py +++ b/execution/executor.py @@ -8,12 +8,12 @@ class Executor(object): ''' - def __init__(self, series): + def __init__(self, series, max_hold_bars): ''' Constructor ''' self.series = series - self.max_hold_bars = 1 + self.max_hold_bars = max_hold_bars def execute(self, signals, long=True): self.trades = [] diff --git a/solver/solver.py b/solver/solver.py index 38c7bb9..4a27a16 100644 --- a/solver/solver.py +++ b/solver/solver.py @@ -25,7 +25,6 @@ class Solver(QObject): super().__init__(None) self.series = series - self.executor = Executor(series) self.generators = [] def add_generator(self, generator): @@ -34,6 +33,8 @@ class Solver(QObject): @QtCore.pyqtSlot(dict) def solve(self, params): max_signals = 5 + max_hold_bars = params.get('max_hold_bars', 1) + self.executor = Executor(self.series, max_hold_bars) max_strategies = params.get('num_strategies', 1000) results = [] diff --git a/ui/mainwindow.py b/ui/mainwindow.py index f4bade1..84fcbc0 100644 --- a/ui/mainwindow.py +++ b/ui/mainwindow.py @@ -10,7 +10,7 @@ from data.signal import PriceComparisonSignalGenerator, RsiSignalGenerator,\ AtrSignalGenerator, DayOfWeekSignalGenerator, CrtdrSignalGenerator,\ AtrDeltaSignalGenerator, SmaSignalGenerator, DayOfMonthSignalGenerator,\ CciSignalGenerator, BbandsSignalGenerator, PivotPointsSignalGenerator,\ - StochasticSignalGenerator + StochasticSignalGenerator, IntradayBarNumberSignalGenerator from PyQt5.Qt import Qt, QFileDialog, QThread, Q_ARG, QMetaObject import pyqtgraph @@ -51,8 +51,10 @@ class MainWindow(QMainWindow, Ui_MainWindow): self.solver.add_generator(BbandsSignalGenerator()) self.solver.add_generator(PivotPointsSignalGenerator()) self.solver.add_generator(StochasticSignalGenerator()) + self.solver.add_generator(IntradayBarNumberSignalGenerator(14)) - params = { 'num_strategies' : self.sb_strategiesNum.value() } + params = { 'num_strategies' : self.sb_strategiesNum.value(), + 'max_hold_bars' : self.sb_maxHoldBars.value() } if self.cb_minTradesFilter.isChecked(): params['min_trades'] = self.sb_minTrades.value() diff --git a/ui/mainwindow.ui b/ui/mainwindow.ui index b036c26..614de87 100644 --- a/ui/mainwindow.ui +++ b/ui/mainwindow.ui @@ -84,7 +84,7 @@ - 100 + 1 10000 @@ -197,6 +197,20 @@ + + + + Max hold bars + + + + + + + 1 + + + diff --git a/ui/ui_mainwindow.py b/ui/ui_mainwindow.py index 36fb68c..cb87711 100644 --- a/ui/ui_mainwindow.py +++ b/ui/ui_mainwindow.py @@ -45,7 +45,7 @@ class Ui_MainWindow(object): self.e_go.setObjectName("e_go") self.gridLayout.addWidget(self.e_go, 1, 9, 1, 1) self.sb_strategiesNum = QtWidgets.QSpinBox(self.centralwidget) - self.sb_strategiesNum.setMinimum(100) + self.sb_strategiesNum.setMinimum(1) self.sb_strategiesNum.setMaximum(10000) self.sb_strategiesNum.setProperty("value", 1000) self.sb_strategiesNum.setObjectName("sb_strategiesNum") @@ -77,6 +77,13 @@ class Ui_MainWindow(object): self.rb_short = QtWidgets.QRadioButton(self.centralwidget) self.rb_short.setObjectName("rb_short") self.gridLayout.addWidget(self.rb_short, 3, 0, 1, 1) + self.label_3 = QtWidgets.QLabel(self.centralwidget) + self.label_3.setObjectName("label_3") + self.gridLayout.addWidget(self.label_3, 2, 2, 1, 1) + self.sb_maxHoldBars = QtWidgets.QSpinBox(self.centralwidget) + self.sb_maxHoldBars.setMinimum(1) + self.sb_maxHoldBars.setObjectName("sb_maxHoldBars") + self.gridLayout.addWidget(self.sb_maxHoldBars, 2, 3, 1, 1) MainWindow.setCentralWidget(self.centralwidget) self.menubar = QtWidgets.QMenuBar(MainWindow) self.menubar.setGeometry(QtCore.QRect(0, 0, 1041, 27)) @@ -112,4 +119,5 @@ class Ui_MainWindow(object): self.cb_minTradesFilter.setText(_translate("MainWindow", "Min. trades:")) self.cb_minWinRate.setText(_translate("MainWindow", "Min. win rate")) self.rb_short.setText(_translate("MainWindow", "Short")) + self.label_3.setText(_translate("MainWindow", "Max hold bars"))