如何在pandas中使用diff()函数,但在新列中输入差值?

问题描述 投票:1回答:1

我有一个数据帧df:

DF

      x-value 
frame 
    1     15  
    2     20 
    3     19

我怎样才能得到:

DF

      x-value   delta-x 
frame 
    1     15      0
    2     20      5
    3     19     -1
pandas dataframe diff difference
1个回答
3
投票

并不是说@Wen发布的评论有什么问题,但我想发布一个更完整的答案。

问题 有三件事情需要解决:

  1. 计算从一行到下一行的差异值。
  2. 处理“差异”将比数据帧的原始长度少一个值的事实,我们将必须填写缺失位的值。
  3. 我们如何将其分配给新列。

选项1 做diff最自然的方法是使用pd.Series.diff(如@Wen建议的那样)。但是为了产生所说的整数结果,我建议使用pd.Series.fillna参数downcast='infer'。最后,我不喜欢编辑数据帧,除非需要它。因此,我使用pd.DataFrame.assign生成一个新数据帧,该数据帧是旧数据集的副本,其中包含新列。

df.assign(**{'delta-x': df['x-value'].diff().fillna(0, downcast='infer')})

       x-value  delta-x
frame                  
1           15        0
2           20        5
3           19       -1

选项#2

类似于#1但我会使用numpy.diff来保留int类型,除了获得一些性能。

df.assign(**{'delta-x': np.append(0, np.diff(df['x-value'].values))})

       x-value  delta-x
frame                  
1           15        0
2           20        5
3           19       -1

测试

pir1 = lambda d: d.assign(**{'delta-x': d['x-value'].diff().fillna(0, downcast='infer')})
pir2 = lambda d: d.assign(**{'delta-x': np.append(0, np.diff(d['x-value'].values))})

res = pd.DataFrame(
    index=[10, 300, 1000, 3000, 10000, 30000],
    columns=['pir1', 'pir2'], dtype=float)

for i in res.index:
    d = pd.concat([df] * i, ignore_index=True)
    for j in res.columns:
        stmt = '{}(d)'.format(j)
        setp = 'from __main__ import d, {}'.format(j)
        res.at[i, j] = timeit(stmt, setp, number=1000)

res.plot(loglog=True)

res.div(res.min(1), 0)

enter image description here

           pir1  pir2
10     2.069498   1.0
300    2.123017   1.0
1000   2.397373   1.0
3000   2.804214   1.0
10000  4.559525   1.0
30000  7.058344   1.0
© www.soinside.com 2019 - 2024. All rights reserved.