Quickstart - cerebro.optstrategy() no result (3.7 Windows)
Hi, I'm new to python and to backtrader. Trying out the quickstart tutorial, everything worked fine, until the optimizer topic, the program does not execute bt.Strategy methods, I put some print values and it seens like the init or stop funcions doesn't execute.
If I change the code to run once, just with cerebro.addstrategy(TestStrategy) it works fine.
When I execute the code, It only prints "calling run()"
from __future__ import (absolute_import, division, print_function, unicode_literals) import datetime # For datetime objects import os.path # To manage paths import sys # To find out the script name (in argv) # Import the backtrader platform import backtrader as bt # Create a Stratey class TestStrategy(bt.Strategy): params = ( ('maperiod', 10), ('printlog', True), ) def log(self, txt, dt=None, doprint=True): ''' Logging function fot this strategy''' if self.params.printlog or doprint: dt = dt or self.datas.datetime.date(0) print('%s, %s' % (dt.isoformat(), txt)) def __init__(self): print('init start') # Keep a reference to the "close" line in the data dataseries self.dataclose = self.datas.close # To keep track of pending orders and buy price/commission self.order = None self.buyprice = None self.buycomm = None # Add a MovingAverageSimple indicator self.sma = bt.indicators.SimpleMovingAverage( self.datas, period=self.params.maperiod) print('init end') def notify_order(self, order): if order.status in [order.Submitted, order.Accepted]: # Buy/Sell order submitted/accepted to/by broker - Nothing to do return # Check if an order has been completed # Attention: broker could reject order if not enough cash if order.status in [order.Completed]: if order.isbuy(): self.log( 'BUY EXECUTED, Price: %.2f, Cost: %.2f, Comm %.2f' % (order.executed.price, order.executed.value, order.executed.comm)) self.buyprice = order.executed.price self.buycomm = order.executed.comm else: # Sell self.log('SELL EXECUTED, Price: %.2f, Cost: %.2f, Comm %.2f' % (order.executed.price, order.executed.value, order.executed.comm)) self.bar_executed = len(self) elif order.status in [order.Canceled, order.Margin, order.Rejected]: self.log('Order Canceled/Margin/Rejected') # Write down: no pending order self.order = None def notify_trade(self, trade): if not trade.isclosed: return self.log('OPERATION PROFIT, GROSS %.2f, NET %.2f' % (trade.pnl, trade.pnlcomm)) def next(self): # Simply log the closing price of the series from the reference self.log('Close, %.2f' % self.dataclose) # Check if an order is pending ... if yes, we cannot send a 2nd one if self.order: return # Check if we are in the market if not self.position: # Not yet ... we MIGHT BUY if ... if self.dataclose > self.sma: # BUY, BUY, BUY!!! (with all possible default parameters) self.log('BUY CREATE, %.2f' % self.dataclose) # Keep track of the created order to avoid a 2nd order self.order = self.buy() else: if self.dataclose < self.sma: # SELL, SELL, SELL!!! (with all possible default parameters) self.log('SELL CREATE, %.2f' % self.dataclose) # Keep track of the created order to avoid a 2nd order self.order = self.sell() def stop(self): self.log('(MA Period %2d) Ending Value %.2f' % (self.params.maperiod, self.broker.getvalue()), doprint=True) if __name__ == '__main__': # Create a cerebro entity cerebro = bt.Cerebro() # Datas are in a subfolder of the samples. Need to find where the script is # because it could have been called from anywhere modpath = os.path.dirname(os.path.abspath(sys.argv)) datapath = 'C:\spy.CSV' # Create a Data Feed data = bt.feeds.YahooFinanceCSVData( dataname=datapath, # Do not pass values before this date fromdate=datetime.datetime(2000, 1, 1), # Do not pass values before this date todate=datetime.datetime(2020, 12, 31), # Do not pass values after this date reverse=False) # Add the Data Feed to Cerebro cerebro.adddata(data) # Set our desired cash start cerebro.broker.setcash(100000.0) # Add a FixedSize sizer according to the stake cerebro.addsizer(bt.sizers.FixedSize, stake=2) # Set the commission cerebro.broker.setcommission(commission=0.0) # Add a strategy strats = cerebro.optstrategy( TestStrategy, maperiod=range(10, 15)) print('calling run()') # Run over everything cerebro.run()
Don't take this personally. It's clear you are new, else you wouldn't miss this at the top of each page in the community.
For code/output blocks: Use ``` (aka backtick or grave accent) in a single line before and after the block. See: http://commonmark.org/help/
which has the effect of making your code readable.
On the positive side you have let us know that you are running under Windows whilst playing with optimization. Further details would have cleared the situation, but the most obvious thing:
- As a newbie you have been sold the benefits of using Jupyter or Spyder or something similar.
Those shells hijack the Python core and eventually destroy the
multiprocessingfacilities of Python under Windows.
See this for example: https://community.backtrader.com/topic/744/optstrategy-not-working-in-jupyter
No, there is nothing which can be done, except that you use a proper shell for executing the scripts.
I didn't understood how to use the backtick, sorry, bad english. It's ok now
I'll search for something to use multiprocessing on windows, I've never used Python, so just installed windows version and followed the tutorial.
I was using IDLE and running the script with F5
It works OK when executed from the command line.
As a suggestion, you could add a warning on the quickstart tutorial, just saying that the optimization uses multiprocessing.