backtrader printing data feed vaues does not print hours and minues and defaults to

1.1k views Asked by At

I'm learning to use backtrader and I've come across a problem when trying to print out the datafeed. It correctly prints the day, open, high, low, close and volume but the hour and minutes data seems to default to 23:59:59.999989 on every line.

Here is a sample of the data source:

datetime,open,high,low,close,volume,,
11/2/2020 9:30,330.187,330.188,329.947,330.038,4.79,,
11/2/2020 9:31,330.038,330.438,329.538,329.677,5.49,,
11/2/2020 9:32,329.667,330.248,329.577,330.117,5.8,,
11/2/2020 9:33,330.128,330.328,329.847,329.948,5.59,,
11/2/2020 9:34,329.967,330.308,329.647,329.698,6.24,,

and the code I use to add the data to backtrader is:

data = bt.feeds.GenericCSVData(
    dataname = 'SPY_11_2020_1M.txt',
    name= 'SPY',
    datetime = 0,
    dtformat = ('%m/%d/%Y %H:%M'),
    period = bt.TimeFrame.Ticks,
    compression = 1,
    fromdate = params['fromdate'], 
    todate = params['todate'],
    open = 1,
    high = 2,
    low = 3,
    close = 4,
    volume = 5,
    openinterest = -1,
    )
cerebro.adddata(data)

my code for the trategy, which is a simple buy and hold strategy, is:

import backtrader as bt
from datetime import datetime as dt

class BuyHold(bt.Strategy):

    def __init__(self):
        # self.time = self.datas[0].datetime.datetime(0),
        self.open = self.datas[0].open
        self.high = self.datas[0].high
        self.low = self.datas[0].low
        self.close = self.datas[0].close
        self.volume = self.datas[0].volume

    def next(self):
        print('{0} {1}\t{2}\t{3}\t{4}\t{5}\t{6}'.format(
            self.datas[0].datetime.date(0),
            self.datas[0].datetime.time(0),
            self.open[0],
            self.high[0],
            self.low[0],
            self.close[0],
            self.volume[0]
            ))

       # print('{0}\t{1}\t{2}\t{3}\t{4}\t{5}'.format(
        #     self.time,
        #     self.open[0],
        #     self.high[0],
        #     self.low[0],
        #     self.close[0],
        #     self.volume[0]
        #     ))

        if self.position.size == 0:
            size = int(self.broker.getcash() / self.data)
            self.buy(size = size)

The printout I get is as:

2020-11-02 23:59:59.999989      330.187 330.188 329.947 330.038 4.79
2020-11-02 23:59:59.999989      330.038 330.438 329.538 329.677 5.49
2020-11-02 23:59:59.999989      329.667 330.248 329.577 330.117 5.8
2020-11-02 23:59:59.999989      330.128 330.328 329.847 329.948 5.59
2020-11-02 23:59:59.999989      329.967 330.308 329.647 329.698 6.24

I also tried it with the commented out self.time with the commented out print line which provides similar result in a slightly different format as:

(datetime.datetime(2020, 11, 2, 23, 59, 59, 999989),)   330.187 330.188 329.947 330.038 4.79
(datetime.datetime(2020, 11, 2, 23, 59, 59, 999989),)   330.038 330.438 329.538 329.677 5.49
(datetime.datetime(2020, 11, 2, 23, 59, 59, 999989),)   329.667 330.248 329.577 330.117 5.8
(datetime.datetime(2020, 11, 2, 23, 59, 59, 999989),)   330.128 330.328 329.847 329.948 5.59
(datetime.datetime(2020, 11, 2, 23, 59, 59, 999989),)   329.967 330.308 329.647 329.698 6.24
(datetime.datetime(2020, 11, 2, 23, 59, 59, 999989),)   329.698 330.198 329.568 329.948 6.51

I don't know what I'm missing here.

2

There are 2 answers

0
7vCC On

This problem also took me few hours. And I find the solution from another web. Here.

For minute data tell cerebro that you are using minute data (timeframe) and how many minutes per bar (compression).

data = bt.feeds.GenericCSVData(
dataname = 'SPY_11_2020_1M.txt',
name= 'SPY',
datetime = 0,

dtformat = ('%m/%d/%Y %H:%M'),
**timeframe=bt.TimeFrame.Minutes,**

period = bt.TimeFrame.Ticks,
compression = 1,
fromdate = params['fromdate'], 
todate = params['todate'],
open = 1,
high = 2,
low = 3,
close = 4,
volume = 5,
openinterest = -1,
)
0
sixsixsix On

struggle with the problem some days,i use isoformat to read the time and date

strategy

class my_strategy1(bt.Strategy):
    def log(self, txt, dt=None):
        ''' Logging function for this strategy'''
        # dt = dt or self.datas[0].datetime.date(0)
        #the fellowing will print date ,that is,2021-08-06
        print(self.datas[0].datetime.date(0).isoformat())
        #the fellowing will print time,that is,08:09:01
        print(self.datas[0].datetime.time(0).isoformat())
        print(txt)
    def __int__(self):
        pass
    def next(self):
        self.log('Close, %.2f' % self.dataclose[0])
        print("trend is", self.datas[0].lines.trend[0])
        pass

data class



class My_CSVData(bt.feeds.GenericCSVData):
    """
    如何添加格外的数据列在excel中进行处理
    how to append the other data to csv
    """
    lines = ('trend',)
    params = (
     ('trend', -1),
)

def get_data_via_excel(path):
    datatest=My_CSVData(
        dataname=path, 
        timeframe=bt.TimeFrame.Minutes, 
        compression=60,
        dtformat='%Y-%m-%d %H:%M:%S',
        tmformat = '%H:%M:%S',
        fromdate = datetime(2021,4,16),
        todate = datetime(2021,7,30),
        datetime = 0,
        high=2,
        open =1,
        close=4,
        low =3,
        volume=5,
        openinterest =6,
        trend = 7 ,#not use -1
        )
    return datatest

data source

datetime,open,high,low,close,volume,openinterest,trend
2021-04-16 09:59:00,5138,5144,5109,5117,200,0,-2
2021-04-16 11:00:00,5117,5122,5089,5102,200,0,-2
2021-04-16 11:29:00,5103,5118,5096,5105,200,0,-1
2021-04-16 14:00:00,5105,5152,5105,5142,200,0,0
2021-04-16 15:00:00,5141,5142,5111,5116,200,0,1
2021-04-16 21:59:00,5122,5141,5116,5129,200,0,0
2021-04-16 23:00:00,5128,5136,5108,5120,200,0,0