提问人:mangosrk 提问时间:4/10/2023 更新时间:4/10/2023 访问量:47
数据帧按列数切片并绘制热图
Dataframe slice by count of columns and draw heatmap
问:
我有一个数据帧。我根据每个内核模块收集了延迟数据。每个模块的时间数据不同3000~1000。我想对数据进行切片,使每个模块的时间大小相等,特别是从 0 到 1000。 下面是我的原始数据帧
time, module_name, latency
0, module1, 268
1, module1, 300
...
999, module1, 300
0, module2, 234
1, module2, 345
...
3000, module2, 345
我对我的数据进行了切片,使其均匀大小为 1000,使用每个模块的 iloc 函数。
trace1000 = df1.groupby('module_name').apply(lambda x: x.iloc[0:999]
结果,我得到了下面的数据帧。 正如我所料,我得到了均匀大小的跟踪,每个模块 1000 个。
module_name, , module_name, latency
module1, 2000, module1, 268
module1, 2001, module1, 300
...
module2, 9085, module1, 234
module2, 9086, module1, 345
...
但是,我不知道为什么我得到重复的列名“module_name”和奇怪的第二列没有名称。 我试图通过这个删除或仅选择列,但失败了。
heat_df = trace1000[["module_name","latency"]]
我的目标是绘制一个 seaborn 热图(x 轴:时间(范围 1-1000),y 轴:module_name(模块数:30,热量:延迟(范围:100~900)。我期待如下图所示的图表
答:
假设我们生成一个较小的示例,由列 、 和 组成。考虑从 0-4 开始,从“module_0”到“module_9”,延迟是一个随机变量。time
module_name
latency
time
module_name
import pandas as pd
import numpy as np
df1 = pd.DataFrame(
{
"time": np.tile(np.arange(0,5),10),
"module_n": np.array([[i]*5 for i in np.arange(10)]).flatten(),
}
).assign(
module_name=lambda x: "module_" + x.module_n.astype(str),
latency=np.random.random(50)
).drop(columns="module_n")
df1
下面是输出的预览:
time module_name latency
0 0 module_0 0.650732
1 1 module_0 0.184202
2 2 module_0 0.741331
3 3 module_0 0.903374
4 4 module_0 0.440044
.. ... ... ...
45 0 module_9 0.024248
46 1 module_9 0.468306
47 2 module_9 0.763958
48 3 module_9 0.556926
49 4 module_9 0.696217
[50 rows x 3 columns]
现在,您要应用一个操作,该操作将获取按列中的值分组的每个子集并执行操作。.groupby
df1
module_name
让我们看一下这些子集之一:
df1_group_module_0 = df1.loc[df1.module_name=="module_0"]
df1_group_module_0
time module_name latency
0 0 module_0 0.650732
1 1 module_0 0.184202
2 2 module_0 0.741331
3 3 module_0 0.903374
4 4 module_0 0.440044
您指定要与 一起应用的操作是 。对于这个较小的示例,假设我只想获取前两个值,因此我将使用 。让我们看看当我们将此操作应用于一个组(我们上面选择的组)时会发生什么:.groupby
lambda x: x.iloc[0:999]
x.iloc[0:2]
df1_group_module_1.iloc[0:2]
time module_name latency
0 0 module_0 0.650732
1 1 module_0 0.184202
你得到的是一个包含列 、 和 的新数据帧,它对应于 的前两行。time
module_name
latency
module_0
将合并对每个组应用上述操作的结果,返回结果并在结果前面加上“module_name”列。这就是为什么你会得到一个额外的列,以及一个额外的列,其中包含组合结果的索引(你可以使用 ..groupby.apply(lambda x: x.iloc[0:2])
module_name
.reset_index(drop=True)
看起来您在这里尝试做的是一个更简单的操作,不需要 groupby:
tr2 = df1.loc[df1.time<=1] # in your case time<=999
time module_name latency
0 0 module_0 0.650732
1 1 module_0 0.184202
5 0 module_1 0.122834
6 1 module_1 0.843534
10 0 module_2 0.108903
.. ... ... ...
36 1 module_7 0.720628
40 0 module_8 0.694778
41 1 module_8 0.649239
45 0 module_9 0.024248
46 1 module_9 0.468306
[20 rows x 3 columns]
另一个只接受前 N 个观测值的选项是使用 .head(N),如以下答案所示 https://stackoverflow.com/a/20069379/3828592
评论