如何在熊猫数据框中计算一天的开始时间,一天的结束时间,每天的平均时间?

时间:2019-06-19 16:34:44

标签: python-3.x pandas dataframe

我有一个数据框:

timestamps                                   values
2017-07-18 20:06:13                            12
2017-07-18 20:08:52                            34
2017-07-19 12:34:02                            123
2017-07-19 12:34:03                            34
2017-07-19 13:11:51                            33
2017-07-19 13:22:08                            76
2017-07-19 22:57:55                            44
2017-07-20 10:34:30                            443
2017-07-20 10:54:00                            32
2017-07-20 11:03:24                            22
2017-07-20 12:05:11                            44
2017-07-20 12:17:28                            323
2017-07-20 12:28:56                            33

时间戳列为datetime64 [ns]。我需要在“时间戳”列中找到每天的开始时间,在“时间戳”列中找到最后一个小时,以及每天的平均计数小时。

我还使用了groupby(),我需要按日期和小时设置索引和分组行:

df = df.set_index('timestamps')
df.groupby([df.index.day,df.index.hour]).count()

我得到了这个结果:

                             values 
timestamps timestamps         
18            20                  2 
19            12                  2 
              13                  2 
              22                  1 
20            10                  2 
              11                  1 
              12                  3 

我无法提取数据帧索引中每天的开始时间,最后一个小时以及每天的平均小时数。我怎么能得到这个?谢谢任何建议。

2 个答案:

答案 0 :(得分:2)

IIUC,您可以尝试以下方法:

df['timestamps'] = pd.to_datetime(df['timestamps'])
df['hour'] = df['timestamps'].dt.hour
df.groupby(df['timestamps'].dt.day).agg({'hour': ['min', 'max', 'mean']}) \
                                   .stack(level=0).droplevel(1)


        min max mean
timestamps          
18      20  20  20.000000
19      12  22  14.400000
20      10  12  11.166667

答案 1 :(得分:1)

为了展示更具启发性的示例,我定义了测试DataFrame 日期不同个月(同样从8月开始)

df = pd.DataFrame(data=[
    [ '2017-07-18 20:06:13',  12 ],
    [ '2017-07-18 20:08:52',  34 ],
    [ '2017-07-19 12:34:02', 123 ],
    [ '2017-07-19 12:34:03',  34 ],
    [ '2017-07-19 13:11:51',  33 ],
    [ '2017-07-19 13:22:08',  76 ],
    [ '2017-07-19 22:57:55',  44 ],
    [ '2017-07-20 10:34:30', 443 ],
    [ '2017-07-20 10:54:00',  32 ],
    [ '2017-07-20 11:03:24',  22 ],
    [ '2017-07-20 12:05:11',  44 ],
    [ '2017-07-20 12:17:28', 323 ],
    [ '2017-07-20 12:28:56',  33 ],
    [ '2017-08-20 11:01:00', 122 ],
    [ '2017-08-20 13:55:58',  44 ]],
    columns=['timestamps', 'values'])
df['timestamps'] = pd.to_datetime(df['timestamps'])

要计算所需的值,请定义要计算的函数 在特定日期的 min max 时间之间的小时数:

def fn(row):
    return (row['max'] - row['min']) / np.timedelta64(1, 'h')

然后运行:

dayLimits = df.groupby(df.timestamps.dt.floor('d'))\
    .agg({'timestamps': [min, max]})
dayLimits.columns = dayLimits.columns.droplevel(0)
dayLimits['hrs'] = dayLimits.apply(fn, axis=1)

此代码:

  • 按日期将 df 分组
  • 每个组的
  • 花费最小和最大时间戳,
  • 删除列多索引的顶级
  • 使用上面定义的函数生成 hrs 列。

对于我的测试数据,结果是:

                           min                 max        hrs
timestamps                                                   
2017-07-18 2017-07-18 20:06:13 2017-07-18 20:08:52   0.044167
2017-07-19 2017-07-19 12:34:02 2017-07-19 22:57:55  10.398056
2017-07-20 2017-07-20 10:34:30 2017-07-20 12:28:56   1.907222
2017-08-20 2017-08-20 11:01:00 2017-08-20 13:55:58   2.916111

现在,每天有几个小时, 每天的小时数,您可以计算为:

dayLimits.hrs.mean()

最后是关于其他答案之一的注释:

dt.day 分组是错误的,因为例如从第20天开始 每个月同一组的成员。

如果您有一个月的日期,这并不明显,但是 在 my 测试DataFrame上尝试使用此代码,这样您就会看到它。

编辑

列名应该不是 Python 的保留字 或例如函数名称。

因此,考虑到上述情况,其他解决方案可以是:

dayLimits = df.groupby(df.timestamps.dt.floor('d'))\
    .agg({'timestamps': [min, max]})
dayLimits.columns = ['tmin', 'tmax']
dayLimits['hrs'] = dayLimits.apply(lambda row:
    (row.tmax - row.tmin) / np.timedelta64(1, 'h'), axis=1)

结果仅在列名上有所不同。