如何将此DataFrame中的信息表示为时间序列?

时间:2016-12-18 01:12:31

标签: python pandas

我有一个像这样的pandas DataFrame:

             start_time             end_time    user
0  2016-12-17 03:10:07   2016-12-17 03:18:10  andrew
1  2016-12-17 03:11:07   2016-12-17 03:15:07   eddie
2  2016-12-17 03:12:08   2016-12-17 03:19:08  andrew  
3  2016-12-17 03:13:08   2016-12-17 03:14:06   eddie
...

每行代表提交给计算群集的作业。 start_time表示计划作业何时开始运行,end_time表示作业已完成。

如何创建按时间索引的新DataFrame,它描述每个用户在给定时刻运行的作业数量?

2 个答案:

答案 0 :(得分:1)

这是一个相当有趣的问题。对于每个用户,您基本上有两个单独的时间序列。第一步是添加一个简单的列,只显示发生的事情(列event)。策略是旋转数据,使得行是时间,列是用户,事件是值。

要创建一个全时系列,我们需要重新采样时间序列(在这种情况下我使用了1秒)并用0填充缺失值(因为没有发生事件。.min().fillna(0)将填充使用NA的数据框然后为零,我认为您可以使用apply(lambda x:...)

来快捷方式
df['event'] = 1
df_starts = df.pivot('start_time', 'user', 'event').fillna(0).resample('1S').min().fillna(0)
df_stops = df.pivot('end_time', 'user', 'event').fillna(0).resample('1S').min().fillna(0)

接下来,我们从两个新数据框创建一个完整索引,因为索引具有非重叠部分。然后使用新索引重新索引两个数据帧。

full_index = df_starts.index.union(df_stops.index)

df_starts = df_starts.reindex(full_index, fill_value=0)
df_stops = df_stops.reindex(full_index, fill_value=0)

最后,从开始事件中减去停止事件构建单个数据帧将是所有事件。开始是正1,止点是负1。在任何给定时间使用.cumsum()获取每个用户的总运行进程。

df_change = df_starts - df_stops
df_running = df_change.cumsum()

这里是df_running的快速图,x轴是自第一次事件以来的秒数。

enter image description here

答案 1 :(得分:1)

这是 a 解决方案。它可能不是最佳的,但似乎工作得很好。当然,我已经生成了自己的数据,并假设用户以零程序运行开始。

String^ calculate(array<Double*>^ Robot_Points_Values, CameraSpacePoint* human_point_cloud, array<unsigned char*>^ bodyindexdata);

以下是表格输出的示例。

import pandas as pd
import datetime as dt

#Generate some data
m = 50
n = 2 * m

start_time = [dt.datetime(2016, 12, 17, 3, np.random.randint(0, 59)) for n in range(n)]

df = pd.DataFrame({'start_time': start_time,
                   'end_time': [date + dt.timedelta(0, np.random.randint(0, 3600)) for date in start_time],
                   'user': ['A', 'E'] * (m)})

#Doing the solution 
user_on = (df.ix[:, ['end_time', 'user']]
             .rename(columns={'end_time':'time'})
             .assign(on_off=-1))
user_off = (df.ix[:, ['start_time', 'user']]
              .rename(columns={'start_time':'time'})
              .assign(on_off=1))

df = pd.concat([user_on, user_off]).sort_values(by='time')
df = df.groupby(['time', 'user']).sum()
df = df.unstack().cumsum().fillna(method='ffill')

比较时间 82ms 来完成10,000个样本,包括生成数据。

这是一个图表,显示了在任何给定时间(红色和紫色)​​,用户随时间运行的程序总数(蓝色和绿色)以及正在运行的程序(ons-offs)的变化。

Cusum vs Change in Programs run per User

注意:在这种情况下,我假设用户可以在给定的时间戳中启动多个程序。这只是我如何生成测试日期的结果。