我正在处理公用事业电表的间隔数据,该数据由时间戳(通常以1小时或15分钟为增量)和能耗值(以kW或kWh为单位)组成。我想迅速将具有单个读数的熊猫数据框转换为带有每月,每小时和每小时平均值,最大值和计数的年度摘要。
年度摘要的格式为12个月x 24小时表(288个单独的单元格),其中每个单元格都是该特定月份和小时内所有值的平均值,最大值或计数。 >
为简单起见,让我们看一下计算计数。(根据建议,我可以推断出对平均值和最大值执行类似的计算。)
我尝试了一种蛮力方法,即按月和小时过滤时间戳(288个值的循环),然后将计数列表到一个矩阵中。但是,这种方法似乎很慢,因为我什至在20米处执行这些计算。我很好奇,是否有更快的方法可以利用pandas / numpy来实现这一点。
以下是间隔数据的格式示例。
from datetime import datetime
import pandas as pd
df = pd.DataFrame()
df["start"] = pd.date_range(start=datetime(2018, 1, 1), end=datetime(2018, 12, 31, 23), freq='900S')
df["value"] = 1
df.set_index("start", inplace=True)
我目前正在按照以下几行进行计算:
for month in range(1, 13):
for hour in range(0, 24):
count = df.query("index.dt.month == {} and index.dt.hour == {}".format(month, hour)).count()
此数据计数的输出如下所示。 (附带说明:有时数据不完整,此表可帮助您识别。)
1 2 3 4 5 6 7 8 9 10 11 12
0 124 112 124 120 124 120 124 124 120 124 120 124
1 124 112 124 120 124 120 124 124 120 124 120 124
2 124 112 124 120 124 120 124 124 120 124 120 124
3 124 112 124 120 124 120 124 124 120 124 120 124
4 124 112 124 120 124 120 124 124 120 124 120 124
5 124 112 124 120 124 120 124 124 120 124 120 124
6 124 112 124 120 124 120 124 124 120 124 120 124
7 124 112 124 120 124 120 124 124 120 124 120 124
8 124 112 124 120 124 120 124 124 120 124 120 124
9 124 112 124 120 124 120 124 124 120 124 120 124
10 124 112 124 120 124 120 124 124 120 124 120 124
11 124 112 124 120 124 120 124 124 120 124 120 124
12 124 112 124 120 124 120 124 124 120 124 120 124
13 124 112 124 120 124 120 124 124 120 124 120 124
14 124 112 124 120 124 120 124 124 120 124 120 124
15 124 112 124 120 124 120 124 124 120 124 120 124
16 124 112 124 120 124 120 124 124 120 124 120 124
17 124 112 124 120 124 120 124 124 120 124 120 124
18 124 112 124 120 124 120 124 124 120 124 120 124
19 124 112 124 120 124 120 124 124 120 124 120 124
20 124 112 124 120 124 120 124 124 120 124 120 124
21 124 112 124 120 124 120 124 124 120 124 120 124
22 124 112 124 120 124 120 124 124 120 124 120 124
23 124 112 124 120 124 120 124 124 120 124 120 124
答案 0 :(得分:4)
您可以使用pandas.crosstab
,然后根据需要使用DataFrame.rename_axis
根据所需的输出删除轴名称。
df_new = (pd.crosstab(df.index.hour, df.index.month)
.rename_axis(None)
.rename_axis(None, axis=1))
[输出]
1 2 3 4 5 6 7 8 9 10 11 12
0 124 112 124 120 124 120 124 124 120 124 120 124
1 124 112 124 120 124 120 124 124 120 124 120 124
2 124 112 124 120 124 120 124 124 120 124 120 124
3 124 112 124 120 124 120 124 124 120 124 120 124
4 124 112 124 120 124 120 124 124 120 124 120 124
5 124 112 124 120 124 120 124 124 120 124 120 124
6 124 112 124 120 124 120 124 124 120 124 120 124
7 124 112 124 120 124 120 124 124 120 124 120 124
8 124 112 124 120 124 120 124 124 120 124 120 124
9 124 112 124 120 124 120 124 124 120 124 120 124
10 124 112 124 120 124 120 124 124 120 124 120 124
11 124 112 124 120 124 120 124 124 120 124 120 124
12 124 112 124 120 124 120 124 124 120 124 120 124
13 124 112 124 120 124 120 124 124 120 124 120 124
14 124 112 124 120 124 120 124 124 120 124 120 124
15 124 112 124 120 124 120 124 124 120 124 120 124
16 124 112 124 120 124 120 124 124 120 124 120 124
17 124 112 124 120 124 120 124 124 120 124 120 124
18 124 112 124 120 124 120 124 124 120 124 120 124
19 124 112 124 120 124 120 124 124 120 124 120 124
20 124 112 124 120 124 120 124 124 120 124 120 124
21 124 112 124 120 124 120 124 124 120 124 120 124
22 124 112 124 120 124 120 124 124 120 124 120 124
23 124 112 124 120 124 120 124 124 120 124 120 124
答案 1 :(得分:1)
我将使用groupby然后将其堆叠:
In [11]: res = df.groupby([df.index.month, df.index.hour])["value"].sum().unstack(0, fill_value=0)
In [12]: res.columns.name = "month" # or None to suppress
In [13]: res.index.name = "hour" # or None to suppress
In [14]: res
Out[44]:
month 1 2 3 4 5 6 7 8 9 10 11 12
hour
0 124 112 124 120 124 120 124 124 120 124 120 124
1 124 112 124 120 124 120 124 124 120 124 120 124
2 124 112 124 120 124 120 124 124 120 124 120 124
3 124 112 124 120 124 120 124 124 120 124 120 124
4 124 112 124 120 124 120 124 124 120 124 120 124
5 124 112 124 120 124 120 124 124 120 124 120 124
6 124 112 124 120 124 120 124 124 120 124 120 124
7 124 112 124 120 124 120 124 124 120 124 120 124
8 124 112 124 120 124 120 124 124 120 124 120 124
9 124 112 124 120 124 120 124 124 120 124 120 124
10 124 112 124 120 124 120 124 124 120 124 120 124
11 124 112 124 120 124 120 124 124 120 124 120 124
12 124 112 124 120 124 120 124 124 120 124 120 124
13 124 112 124 120 124 120 124 124 120 124 120 124
14 124 112 124 120 124 120 124 124 120 124 120 124
15 124 112 124 120 124 120 124 124 120 124 120 124
16 124 112 124 120 124 120 124 124 120 124 120 124
17 124 112 124 120 124 120 124 124 120 124 120 124
18 124 112 124 120 124 120 124 124 120 124 120 124
19 124 112 124 120 124 120 124 124 120 124 120 124
20 124 112 124 120 124 120 124 124 120 124 120 124
21 124 112 124 120 124 120 124 124 120 124 120 124
22 124 112 124 120 124 120 124 124 120 124 120 124
23 124 112 124 120 124 120 124 124 120 124 120 124
注意:我得到了不同的值,我得到了〜120,因为每小时4次乘以每月的天数(某些月份比其他月份更长)...