代码之家  ›  专栏  ›  技术社区  ›  Antoine Viscardi Ziyed

降幅积和

  •  3
  • Antoine Viscardi Ziyed  · 技术社区  · 6 年前

    我正在实现一个小型的python应用程序来衡量交易策略的回报。计算返回的函数接受以下输入:

    • 包含收盘价的熊猫数据框架
    • 代表购买信号的大熊猫的一系列胸部
    • 代表出售信号的大熊猫的一系列胸部
    • 代表交易费用占初始资本百分比的浮动

    数据如下所示:

    >>>df.head())
    开-高-低-关音量
    日期
    2015年1月2日5.34 5.37 5.11 5.21 108469
    2015-01-05 5.21 5.26 4.85 4.87 160089
    2015年1月6日4.87 4.87 4.55 4.57 316501
    2015年1月7日4.63 4.75 4.60 4.67 15117
    2015年1月8日4.69 4.89 4.69 4.81 159294
    >>>
    

    购买.head())
    2015-01-02正确
    2015-01-05错误
    2015-01-06错误
    2015-01-07错误
    2015-01-08错误
    数据类型:bool
    >>>
    

    不考虑费用,这是计算比率的公式:

    其中,cis the initial capital andriis the return of one buy/sell trade.

    这可以使用矢量化实现轻松实现:

    buy_sell=df[(buy==true)(sell==true)]
    价格=买入卖出收盘价
    diffs=价格-价格.shift()
    比率=差价/价格.shift()
    返回((比率+1).product(轴=0)
    

    当考虑到费用的时候,我得出了以下公式:

    其中,fis the trading fee.

    这可以很容易地使用循环来实现,但是有没有一种方法可以通过矢量化实现来实现呢?

    我不是一个数学专家,但可能是产品依赖于总和指数阻止了这一点?我在网上找过这个房子,但好像什么也找不到。也许我没有正确地阐述问题,因为我缺乏技术术语。

    对此有任何想法都将不胜感激:)


    编辑

    根据DSM的答案,解决方案是对反向比率序列执行“累积积”。这给了我以下解决方案:

    def compute_return(df,buy,sell,fees=0.):
    
    #对数据执行的一系列验证操作
    
    买入卖出=df[(买入=true)(卖出=true)]
    价格=买入卖出收盘价
    diffs=价格-价格.shift()
    比率=差价/价格.shift()
    
    cum_prod=(比率+1)[1:][:-1].cumprod())
    
    返回((1-费用)*(比率+1).product(axis=0)-费用*cum_prod.sum())
    
  • 包含收盘价的熊猫数据框架
  • 代表购买信号的大熊猫的一系列胸部
  • 代表出售信号的大熊猫的一系列胸部
  • 代表交易费用占初始资本百分比的浮动
  • 数据如下:

    >>> df.head()
                open  high   low  close  volume
    date                                       
    2015-01-02  5.34  5.37  5.11   5.21  108469
    2015-01-05  5.21  5.26  4.85   4.87  160089
    2015-01-06  4.87  4.87  4.55   4.57  316501
    2015-01-07  4.63  4.75  4.60   4.67  151117
    2015-01-08  4.69  4.89  4.69   4.81  159294
    >>> 
    

    >>> buy.head()
    2015-01-02     True
    2015-01-05    False
    2015-01-06    False
    2015-01-07    False
    2015-01-08    False
    dtype: bool
    >>>
    

    在不考虑费用的情况下,这是计算比率的公式:

    在哪里?C是初始资本和ri是一次买卖交易的回报。

    这可以使用矢量化实现轻松实现:

    buy_sell = df[(buy==True)|(sell==True)]
    prices = buy_sell.close
    diffs = prices - prices.shift()
    ratios = diffs / prices.shift()
    return ((ratios + 1).product(axis=0))
    

    当考虑到费用时,我得出以下公式:

    enter image description here

    在哪里?f是交易费。

    这可以很容易地使用循环来实现,但是有没有一种方法可以通过矢量化实现来实现呢?

    我不是一个数学专家,但可能是产品依赖于总和指数阻止了这一点?我在网上找过这个房子,但好像什么也找不到。也许我没有正确地阐述这个问题,因为我缺乏技术术语。

    对此有任何想法都将不胜感激:)


    编辑

    根据DSM的答案,解决方案是对反向比率序列执行“累积积”。这给了我以下解决方案:

    def compute_return(df, buy, sell, fees=0.):
    
        # Bunch of verifications operation performed on data
    
        buy_sell = df[(buy==True)|(sell==True)]
        prices = buy_sell.close
        diffs = prices - prices.shift()
        ratios = diffs / prices.shift()
    
        cum_prod = (ratios + 1)[1:][::-1].cumprod()
    
        return ((1 - fees) * (ratios + 1).product(axis=0) - fees * cum_prod.sum())
    
    1 回复  |  直到 6 年前
        1
  •  1
  •   DSM    6 年前

    我觉得这个还不错。从A ratios 喜欢

    In [95]: ratios
    Out[95]: 
    date
    2015-01-02         NaN
    2015-01-05   -0.065259
    2015-01-06   -0.061602
    2015-01-07    0.021882
    2015-01-08    0.029979
    Name: close, dtype: float64
    

    我们有(这里我们只关注“新”的第二学期):

    def manual(rs):
        return sum(np.prod([1+rs.iloc[j] for j in range(i, len(rs))]) 
                   for i in range(2, len(rs)))
    

    def vectorized(rs):
        rev = 1 + rs.iloc[2:].iloc[::-1]
        return rev.cumprod().sum()
    

    也就是说,我们只需要取 反向 从头到尾。

    这给了我:

    In [109]: manual(ratios)
    Out[109]: 3.07017466956023
    
    In [110]: vectorized(ratios)
    Out[110]: 3.07017466956023
    

    (我不太关心我们是应该用2还是1作为这里的偏移量,还是把 f 因素——这些是很容易改变的。)