For code/output blocks: Use ``` (aka backtick or grave accent) in a single line before and after the block. See: http://commonmark.org/help/

MultiData Strategy excludes older data points from different feeds



  • I am trying to include fundamental data for along with ohlc for single ticker as data feed. I add multiple datafeeds and try to run cerebro for validation. But i can see the data used for backtesting shows data only when all the data feeds are available.
    Is this expected behavior ?

    try:
        del cerebro
    except NameError:
        pass
    
    cerebro = bt.Cerebro()
    
    selected_daily_columns       = ['open', 'high', 'low', 'close', 'volume']
    selected_fundamental_columns = ["debt","cashneq","equity","de"]
    
    custom_params = [('datetime', "date"), ('openinterest',None)]
    custom_params += [(name, name) for name in selected_daily_columns]
    custom_params += [(name, name) for name in selected_fundamental_columns]
    
    class PandasCustomData(bt.feeds.PandasData):
        lines = tuple(selected_fundamental_columns)
        params = tuple(custom_params)
        
    ticker_data_feed = ['LCTX', 'PTN', 'XXII', 'CSLT']
    ticker_data_feedi = {k: v for v, k in enumerate(ticker_data_feed)}
    
    for ticker in ticker_data_feed:
        data_sep_ = data_sep[data_sep.ticker == ticker]
        data_sf1_ = data_sf1[data_sf1.ticker == ticker]
        df_ = data_sep_.merge(data_sf1_.rename({"datekey":"date"}, axis=1),
                        on=["ticker","date"], how="left").sort_values(by="date")
        print(f"{ticker} min_date:{df_.date.min()}")
        pd_data_feed = PandasCustomData(dataname=df_, name=ticker)
        del df_, data_sep_, data_sf1_
        gc.collect()
        
        cerebro.adddata(pd_data_feed)
        
    class TestStrategy(bt.Strategy):
    
        def log(self, txt, dt=None):
            ''' Logging function for this strategy'''
            dt = dt or self.datas[0].datetime.date(0)
            print('%s, %s' % (dt.isoformat(), txt))
    
        def __init__(self):
            # Keep a reference to the "close" line in the data[0] dataseries
            pass
    
    
        def next(self):
            # Simply log the closing price of the series from the reference
            msg = ""
            for ticker,tickeri in ticker_data_feedi.items():
                msg += f' ;{ticker} Close:{self.datas[tickeri].close[0]:.2f}'
                msg += "" if pd.isna(self.datas[tickeri].equity[0]) else f' Equity:{self.datas[tickeri].equity[0]}'
                msg += "" if pd.isna(self.datas[tickeri].de[0]) else f' DE:{self.datas[tickeri].de[0]}'
    
            self.log( msg )
            
    # Add a strategy
    cerebro.addstrategy(TestStrategy)
    
    # Add a FixedSize sizer according to the stake
    cerebro.addsizer(bt.sizers.FixedSize, stake=20)
    
    # Set our desired cash start
    cerebro.broker.setcash(10000.0)
    # Set the commission - 0.1% ... divide by 100 to remove the %
    cerebro.broker.setcommission(commission=0.001)
    
    # Print out the starting conditions
    print('Starting Portfolio Value: %.2f' % cerebro.broker.getvalue())
    # Run over everything
    cerebro.run(oldsync=False)
    # Print out the final result
    print('Final Portfolio Value: %.2f' % cerebro.broker.getvalue())
    

    The output shows starts as

    LCTX min_date:1997-12-31 00:00:00
    PTN min_date:1997-12-31 00:00:00
    XXII min_date:2011-01-26 00:00:00
    CSLT min_date:2014-03-14 00:00:00
    Starting Portfolio Value: 10000.00
    2014-03-14,  ;LCTX Close:3.71 ;PTN Close:1.04 ;XXII Close:4.60 ;CSLT Close:39.80
    2014-03-17,  ;LCTX Close:3.57 Equity:14800768.0 DE:1.045 ;PTN Close:1.08 ;XXII Close:4.44 ;CSLT Close:37.25
    2014-03-18,  ;LCTX Close:3.45 ;PTN Close:1.09 ;XXII Close:4.35 ;CSLT Close:33.65
    2014-03-19,  ;LCTX Close:3.38 ;PTN Close:1.26 ;XXII Close:3.79 ;CSLT Close:31.50
    2014-03-20,  ;LCTX Close:3.51 ;PTN Close:1.23 ;XXII Close:3.98 ;CSLT Close:31.99
    2014-03-21,  ;LCTX Close:3.52 ;PTN Close:1.44 ;XXII Close:3.53 ;CSLT Close:29.35
    2014-03-24,  ;LCTX Close:3.36 ;PTN Close:1.29 ;XXII Close:2.69 ;CSLT Close:27.33
    2014-03-25,  ;LCTX Close:3.37 ;PTN Close:1.30 ;XXII Close:3.22 ;CSLT Close:25.90
    2014-03-26,  ;LCTX Close:3.26 ;PTN Close:1.20 ;XXII Close:3.16 ;CSLT Close:24.77
    2014-03-27,  ;LCTX Close:3.24 ;PTN Close:1.18 ;XXII Close:3.13 ;CSLT Close:23.46
    ....
    


  • Yes, this is expected default behavior. To use all history you need to use both prenext() and next() calls. This was discussed on the forum several times, search for it.


Log in to reply
 

});