Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/loops/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Function 带类的backtrader循环函数_Function_Loops_Class_Backtrader - Fatal编程技术网

Function 带类的backtrader循环函数

Function 带类的backtrader循环函数,function,loops,class,backtrader,Function,Loops,Class,Backtrader,有一个pickle文件有许多(比如10个)股票名称 还有一个包含所有股票数据的文件夹 我试着运行代码来做MACD分析,希望能写下结果买卖时间,价格,头寸,手头现金。 当我走到这一步,试图在所有股票上运行MACD时。 但经过两次循环后,数据加载是错误的。并重复结果 ''' import backtrader as bt import pandas as pd import pickle import math def run_test_macd(): with open("s

有一个pickle文件有许多(比如10个)股票名称 还有一个包含所有股票数据的文件夹 我试着运行代码来做MACD分析,希望能写下结果买卖时间,价格,头寸,手头现金。 当我走到这一步,试图在所有股票上运行MACD时。 但经过两次循环后,数据加载是错误的。并重复结果

'''
import backtrader as bt
import pandas as pd
import pickle
import math


def run_test_macd():
    with open("sp500tickers.pickle", "rb") as f:
        tickers = pickle.load(f)
    cerebro.addstrategy(GoldenCross.gold_cross_class)
    for ticker in tickers:
        macd_stock_test2(ticker)

def macd_stock_test2(ticker):
    # print("stock test")
    # print("ticker")
    cerebro.broker.set_cash(1000000)
    ticker_prices = pd.read_csv('stock_dfs/{}.csv'.format(ticker), index_col='Date', parse_dates=True)

    # print(ticker_prices)
    # ticker prices
    feed = bt.feeds.PandasData(dataname=ticker_prices)
    print(feed)
    print(ticker)
    cerebro.adddata(feed)

    # cerebro.addsizer(bt.sizers.FixedSize, stake=1000)
    # cerebro.addanalyzer(btanalyzers.DrawDown, _name='drawdown')
    # cerebro.addanalyzer(btanalyzers.DrawDown, _name='returns')

    print('starting protfolio value: %.2f' % cerebro.broker.getvalue())
    cerebro.run()

    print('final protfolio value: %.2f' % cerebro.broker.getvalue())
    # cerebro.addanalyzer(SQN)
    #
    # cerebro.addwriter(bt.WriterFile, csv=args.writercsv, rounding=2)
    # cerebro.plot(style='candle')

class gold_cross_class(bt.Strategy):

    #set parameters to define fast and slow
    params = (('fast',40),('slow',150),('order_percentage',0.99),('ticker', "stock"))

    #define constractors
    def __init__(self):
        print("position size:",self.position.size)

        self.fast_moving_average=bt.indicators.EMA(
            self.data.close, period=self.params.fast, plotname='40 day moving average'
        )

        self.slow_moving_average = bt.indicators.EMA(
            self.data.close,  period=self.params.slow, plotname='150 day moving average'
        )

        self.crossover = bt.indicators.CrossOver(self.fast_moving_average, self.slow_moving_average)

    def next(self):
        if self.position.size == 0:
            if self.crossover >0:
                amount_to_invest = (self.params.order_percentage *self.broker.cash)
                self.size=math.floor(amount_to_invest/self.data.close)

                print("Buy {} shares of {} at {} on {}".format(self.size,self.params.ticker, self.data.close[0],self.data.close[0]))
                self.buy(size=self.size)

        if self.position.size > 0:
            if self.crossover<0:
                print("Sell {} shares of {} at {}".format(self.size,self.params.ticker, self.data.close[0]))
                self.sell(size=self.size)
'''
“”
作为bt的进口反向交易者
作为pd进口熊猫
进口泡菜
输入数学
def run_test_macd():
打开(“sp500tickers.pickle”、“rb”)作为f:
tickers=pickle.load(f)
大脑添加策略(黄金交叉、黄金交叉类)
对于自动售检票机中的自动售检票机:
macd_股票测试2(股票代码)
def macd_股票测试2(股票代码):
#打印(“库存测试”)
#打印(“股票代码”)
脑波经纪商套现(1000000)
ticker\u prices=pd.read\u csv('stock\u dfs/{}.csv'.格式(ticker),index\u col='Date',parse\u dates=True)
#打印(股票价格)
#股票价格
feed=bt.feed.PandasData(dataname=ticker\u prices)
打印(提要)
打印(股票代码)
大脑添加数据(提要)
#大脑加法器(bt.sizers.FixedSize,桩号=1000)
#Cerbero.addanalyzer(btanalyzers.DrawDown,\u name='DrawDown')
#cerebro.addanalyzer(btanalyzers.DrawDown,_name='returns')
打印('开始的protofolio值:%.2f'%Cerbero.broker.getvalue())
脑波跑
打印('final protfolio value:%.2f'%Cerbero.broker.getvalue())
#大脑分析仪(SQN)
#
#cerebro.addwriter(bt.WriterFile,csv=args.writersv,舍入=2)
#脑波图(style='candle')
黄金级\交叉级(bt.Strategy):
#设置参数以定义快速和慢速
参数=('fast',40),('slow',150),('order_percentage',0.99),('ticker',“stock”))
#定义承包商
定义初始化(自):
打印(“位置大小:”,self.position.size)
self.fast\u moving\u average=bt.indicators.EMA(
self.data.close,period=self.params.fast,plotname='40天移动平均线'
)
self.slow\u moving\u average=bt.indicators.EMA(
self.data.close,period=self.params.slow,plotname='150天移动平均线'
)
self.crossion=bt.indicators.crossion(self.fast\u moving\u average,self.slow\u moving\u average)
def next(自我):
如果self.position.size==0:
如果self.crossion>0:
投资金额=(self.params.order\u百分比*self.broker.cash)
self.size=math.floor(投资金额/self.data.close)
打印(“在{}上的{}购买{}的{}股份”。格式(self.size,self.params.ticker,self.data.close[0],self.data.close[0]))
self.buy(大小=self.size)
如果self.position.size>0:

如果self.crossover请在代码开头的docstring中查看我的注释。由于我没有你的数据,我已经注释掉了你的一些数据加载,这样我才能加载我自己的数据

import datetime
import backtrader as bt
import pandas as pd
import pickle
import math

"""
You have a number of issues. 
1. Establish cerebro in `macd_stock_test2` 
2. Call the `run_test_macd` from if __name__ == "__main__":
3. Add in print log
4. Add in order and trade notify.
5. Don't pass in the strategy, create it in `macd_stock_test2`.
6. Change name of GoldCross class to python standard.

"""


def run_test_macd():
    # with open("sp500tickers.pickle", "rb") as f:
    #     tickers = pickle.load(f)
    tickers = ["TSLA", "FB"]
    for ticker in tickers:
        macd_stock_test2(ticker)


def macd_stock_test2(ticker):
    # print("stock test")
    # print("ticker")
    cerebro = bt.Cerebro()
    cerebro.addstrategy(GoldCross)

    cerebro.broker.set_cash(1000000)
    # ticker_prices = pd.read_csv(
    #     "stock_dfs/{}.csv".format(ticker), index_col="Date", parse_dates=True
    # )

    # print(ticker_prices)
    # ticker prices
    # feed = bt.feeds.PandasData(dataname=ticker_prices)
    # print(feed)
    # print(ticker)
    feed = bt.feeds.YahooFinanceData(
        dataname=ticker,
        timeframe=bt.TimeFrame.Days,
        fromdate=datetime.datetime(2019, 1, 1),
        todate=datetime.datetime(2020, 12, 31),
        reverse=False,
    )
    cerebro.adddata(feed)

    # cerebro.addsizer(bt.sizers.FixedSize, stake=1000)
    # cerebro.addanalyzer(btanalyzers.DrawDown, _name='drawdown')
    # cerebro.addanalyzer(btanalyzers.DrawDown, _name='returns')

    print("starting portfolio value: %.2f" % cerebro.broker.getvalue())
    cerebro.run()

    print("final portfolio value: %.2f" % cerebro.broker.getvalue())
    # cerebro.addanalyzer(SQN)
    #
    # cerebro.addwriter(bt.WriterFile, csv=args.writercsv, rounding=2)
    # cerebro.plot(style='candle')


class GoldCross(bt.Strategy):

    # set parameters to define fast and slow
    params = (
        ("fast", 40),
        ("slow", 150),
        ("order_percentage", 0.99),
        ("ticker", "stock"),
    )

    # define constractors
    def __init__(self):
        print("position size:", self.position.size)

        self.fast_moving_average = bt.indicators.EMA(
            self.data.close, period=self.params.fast, plotname="40 day moving average"
        )

        self.slow_moving_average = bt.indicators.EMA(
            self.data.close, period=self.params.slow, plotname="150 day moving average"
        )

        self.crossover = bt.indicators.CrossOver(
            self.fast_moving_average, self.slow_moving_average
        )

    def log(self, txt, dt=None):
        """ Logging function fot this strategy"""
        dt = dt or self.data.datetime[0]
        if isinstance(dt, float):
            dt = bt.num2date(dt)
        print("%s, %s" % (dt.date(), txt))

    def notify_order(self, order):
        """ Triggered upon changes to orders. """

        # Suppress notification if it is just a submitted order.
        if order.status == order.Submitted:
            return

        # Print out the date, security name, order number and status.
        dt, dn = self.datetime.date(), order.data._name
        type = "Buy" if order.isbuy() else "Sell"
        self.log(
            f"{order.data._name:<6} Order: {order.ref:3d}\tType: {type:<5}\tStatus"
            f" {order.getstatusname():<8} \t"
            f"Size: {order.created.size:9.4f} Price: {order.created.price:9.4f} "
            f"Position: {self.getposition(order.data).size}"
        )
        if order.status == order.Margin:
            return

        # Check if an order has been completed
        if order.status in [order.Completed]:
            self.log(
                f"{order.data._name:<6} {('BUY' if order.isbuy() else 'SELL'):<5} "
                # f"EXECUTED for: {dn} "
                f"Price: {order.executed.price:6.2f} "
                f"Cost: {order.executed.value:6.2f} "
                f"Comm: {order.executed.comm:4.2f} "
                f"Size: {order.created.size:9.4f} "
            )

    def notify_trade(self, trade):
        """Provides notification of closed trades."""
        if trade.isclosed:
            self.log(
                "{} Closed: PnL Gross {}, Net {},".format(
                    trade.data._name,
                    round(trade.pnl, 2),
                    round(trade.pnlcomm, 1),
                )
            )

    def next(self):
        if self.position.size == 0:
            if self.crossover > 0:
                amount_to_invest = self.params.order_percentage * self.broker.cash
                self.size = math.floor(amount_to_invest / self.data.close)

                self.log(
                    "Buy {} shares of {} at {}".format(
                        self.size,
                        self.params.ticker,
                        self.data.close[0],
                    )
                )
                self.buy(size=self.size)

        if self.position.size > 0:
            if self.crossover < 0:
                self.log(
                    "Sell {} shares of {} at {}".format(
                        self.size, self.params.ticker, self.data.close[0],
                    )
                )
                self.sell(size=self.size)


if __name__ == "__main__":
    run_test_macd()


我想显示购买日期“打印”(“在{}上购买{}的{}股份)。格式(self.size,self.params.ticker,self.data.close[0],self.data.date[0])”。有一条错误消息:“AttributeError:'Lines\LineSeries\udataseries\uohlc\uohlcdatetime\uAbst'对象没有属性“date”.将其用于日期:self.data.datetime[0]我在这段代码中遇到了一些问题。1.实际交易价格(记录在文件中)与输出不同。2/实际交易价格不是开盘价低收盘价高收盘价。3.当订单百分比设置为100%时,通常显示订单状态:保证金和订单取消,即使现金足以支持交易。我将代码更改为“self.buy(size=self.size,price=self.data.close[0])”self.sell(size=self.size,price=self.data.close[0])仍然无法解决问题。您需要一个缓冲区:
self.size=math.floor(amount\u-to\u-invest/self.data.close)
如果您尝试投资全部金额,计算股票时,如果价格下一条上涨,没有足够的现金购买。试试这个
self.size=math.floor((amount\u to\u invest*.9)/self.data.close)
根据股票的波动性,可以使用.98或更高。只是实验。
实际交易价格(写在文件中)与输出不同。2/实际交易价格不是任何开盘价-低-高-收盘价调整-收盘价。
您使用的是
市场
订单,检查您的数据,这应该在下一个开盘时进行交易。用完,您帮了大忙。我对这个很陌生。非常感谢你的好意。我添加了两张图片。显示买入/卖出订单价格和头寸问题。您的代码运行,但买入价和卖出价不正确。我在帖子上贴了两张新照片。你能看见吗?
starting protfolio value: 1000000.00
position size: 0
2019-10-28, Buy 15105 shares of stock at 65.54
2019-10-29, TSLA   Order:   1   Type: Buy   Status Accepted     Size: 15105.0000 Price:   65.5400 Position: 15105
2019-10-29, TSLA   Order:   1   Type: Buy   Status Completed    Size: 15105.0000 Price:   65.5400 Position: 15105
2019-10-29, TSLA   BUY   Price:  64.00 Cost: 966720.00 Comm: 0.00 Size: 15105.0000 
final protfolio value: 10527931.90
starting protfolio value: 1000000.00
position size: 0
2020-05-12, Buy 4712 shares of stock at 210.1
2020-05-13, FB     Order:   2   Type: Buy   Status Accepted     Size: 4712.0000 Price:  210.1000 Position: 4712
2020-05-13, FB     Order:   2   Type: Buy   Status Completed    Size: 4712.0000 Price:  210.1000 Position: 4712
2020-05-13, FB     BUY   Price: 209.43 Cost: 986834.16 Comm: 0.00 Size: 4712.0000 
final protfolio value: 1294217.28

Process finished with exit code 0