【问题标题】:Create time series dataframe with sliding windows使用滑动窗口创建时间序列数据框
【发布时间】:2020-10-02 04:50:13
【问题描述】:

我有一个如下所示的数据集:

     A  B
5/8  2  3 
6/8  4  2
7/8  3  5 
8/8  3  2
 

我想这样结束

index1 index2   A  B
5/8      5/8    2  3
         6/8    4  2
6/8      6/8    4  2
         7/8    3  5
7/8      7/8    3  5
         8/8    3  2
 etc.

也是一个可以采用数字索引的等价物。这样我就可以决定是展平数据还是为 ML 训练创建一个 3d 数组。

我已经用 df.iterrows() 完成了它,但它太慢了。我也尝试过制作这段代码:

  def addDatas(x,df,window):
    global dfOo #Dataset to create
    if len(x)==window:
      y = df.loc[x.index];
      y.DateStarted  = df.loc[x.index[-1]].created #index1 in table presented
      dfOo = dfOo.append(y)
      return 0;
  dfOo= pd.DataFrame();
  #created is the date index in the first table
  dfTargets.rolling("5s",on="created").apply(lambda x : addDatas(x,dfTargets,5))

这两种解决方案都有效,但速度不够快,并且无法处理大量数据。我可以帮忙,但我认为一定有一种我不知道的更简单的方法来做到这一点。

【问题讨论】:

    标签: time-series pandas


    【解决方案1】:

    以下内容适用于任何可排序的索引。它确实会在内存中创建数据帧的副本,因此如果您受到内存限制,这是此方法的一个缺点。

    import pandas as pd
    
    # Minimal example
    df = pd.DataFrame(data={'index':['5/8','6/8','7/8','8/8'],'A':[2,4,3,3],'B':[3,2,5,2]})
    
    # Create a shifted version of the index 'index' column
    df['index_2'] = df['index'].shift()
    
    # Copy to df2, renaming columns and dropping null value (first shifted row)
    df2 = df.copy().rename({'index':'index_2','index_2':'index'},axis=1).dropna()
    
    # In original df overwrite index_2 to be equal to index column
    df['index_2'] = df['index']
    
    # Concatenate, set index, and sort by index
    pd.concat([df,df2]).set_index(['index','index_2']).sort_index()
    

    输出:

                    A   B
    index   index_2         
    5/8     5/8     2   3
            6/8     4   2
    6/8     6/8     4   2
            7/8     3   5
    7/8     7/8     3   5
            8/8     3   2
    8/8     8/8     3   2
    

    【讨论】:

    • 太棒了!这比我做的要简单得多。非常感谢
    【解决方案2】:

    我想提出一个使用np.repeat 的解决方案。 我们将首先加载数据:

    df = pd.DataFrame({'A':[2,4,3,3], 'B':[3,2,5,2]}, index=['5/8', '6/8', '7/8', '8/8'])
    

    我们首先生成一个列表,称为 xi,它的长度值为 2,但第一个和最后一个元素除外。

    xi=[2]*len(df)
    xi[0]=1
    xi[-1]=1
    

    此列表将在np.repeat 中用于重复所需的元素。 基本上,以下给出了所需的数据,除了缺少索引:

    ndf = df.loc[np.repeat(df.index.values, xi)]
    

    下面准备一级索引:

    ndf.set_index([np.repeat(ndf.index, [2,0]*int(len(ndf)/2)), ndf.index])
    

    【讨论】:

      猜你喜欢
      • 2014-01-22
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-10-19
      • 1970-01-01
      • 2020-02-06
      • 2022-06-21
      相关资源
      最近更新 更多