0

假设我有

df

                          ts  v
0 2014-11-03 03:39:42.200914  1
1 2014-11-03 03:39:42.500914  2
2 2014-11-03 03:39:43.600914  3
3 2014-11-03 03:39:43.620914  4

我想附加一个列 s,这样在每一行中,它都包含v1 秒回溯时间间隔内 s 的总和,例如

desired_df
   s                         ts  v
0  1 2014-11-03 03:39:42.200914  1
1  3 2014-11-03 03:39:42.500914  2
2  3 2014-11-03 03:39:43.600914  3
3  7 2014-11-03 03:39:43.620914  4

那么,如何生成这个额外的列s

不,间隔应该重叠,但它们必须在数据帧中的每一行(数据点)都有正确的端点,即我的数据帧中的每一行(数据点)必须是该大小间隔的右端点。

编辑:下面的答案不正确?完成

编辑:我希望该解决方案适用于通用时间间隔,例如 14 毫秒,不一定只是 1 秒。

怎么样

df['s'] = df.groupby(pd.TimeGrouper(freq='400mS')).transform(numpy.cumsum)

我有

                          ts  v  s
0 2014-11-03 03:39:42.200914  1  1
1 2014-11-03 03:39:42.500914  2  2
2 2014-11-03 03:39:43.600914  3  3
3 2014-11-03 03:39:43.620914  4  7

索引为 1 的行不是错误的吗?s 在 03:39:42.500914 应该是 2+1=3。不是2,因为前2行在400ms内,所以应该把它们加在一起。为什么不这样做?

编辑:当我尝试

df['s'] = df.groupby(pd.TimeGrouper(freq='340mS')).transform(numpy.cumsum)

它实际上执行该分组,即使时间间隔更小:

                            v  s
ts                              
2014-11-03 03:39:42.200914  1  1
2014-11-03 03:39:42.500914  2  3
2014-11-03 03:39:43.600914  3  3
2014-11-03 03:39:43.620914  4  7

那么,TimeGrouper 放置的分隔符(分隔符)在哪里?我希望间隔的右端点与我正在查看的行重合(s 对应的行)

4

1 回答 1

3

设置ts为索引,然后设置为groupby第二,并转换cumsum()为新列s,然后应用reset_index,如下所示:

df
                          ts  v
0 2014-11-03 03:39:42.200914  1
1 2014-11-03 03:39:42.500914  2
2 2014-11-03 03:39:43.600914  3
3 2014-11-03 03:39:43.620914  4

df = df.set_index('ts')

df['s'] = df.groupby(lambda x: x.second).transform(cumsum)
df = df.reset_index()
df

                          ts  v  s
0 2014-11-03 03:39:42.200914  1  1
1 2014-11-03 03:39:42.500914  2  3
2 2014-11-03 03:39:43.600914  3  3
3 2014-11-03 03:39:43.620914  4  7

您可能需要重新排序列:

df = df[['s','ts','v']]
df
   s                         ts  v
0  1 2014-11-03 03:39:42.200914  1
1  3 2014-11-03 03:39:42.500914  2
2  3 2014-11-03 03:39:43.600914  3
3  7 2014-11-03 03:39:43.620914  4

更新

由于需要通用方法的 OP 更新,pd.TimeGrouper可以使用:

另一个更新(提供完整步骤)

df = pd.DataFrame([['2014-11-03 03:39:42.200914',1],['2014-11-03 03:39:42.500914', 2],['2014-11-03 03:39:43.600914',3],['2014-11-03 03:39:43.620914', 4]], columns=['ts','v'], dtype=object)

# you will get type error if you haven't converted your string to datetime 
df['ts'] = [pd.to_datetime(d) for d in df['ts']]

df = df.set_index('ts')

看到这条线

# from the doc we need to add closed='left' to include the first nbin count
df['s'] = df.groupby(pd.TimeGrouper(freq='340mS', closed='left')).transform(cumsum)

# reset the index
df = df.reset_index()

# reorder the columns
df = df[['s', 'ts', 'v']]

df
   s                         ts  v
0  1 2014-11-03 03:39:42.200914  1
1  3 2014-11-03 03:39:42.500914  2
2  3 2014-11-03 03:39:43.600914  3
3  7 2014-11-03 03:39:43.620914  4

然而,在“400mS”上,我同意我们仍然没有得到想要的结果。

于 2014-11-03T16:46:52.817 回答