python - 如何在 Pandas 中优化/替换这 2 个嵌套的 While 循环
问题描述
我是 Python 新手,所以很高兴能走到这一步!我有一个包含 1,700,000 条记录和 4 列 (e,n,o,p) + 索引的数据框 (df1),这是大量预处理和连接的结果。
目前这段代码需要 2 个小时才能运行,很明显,n 的 1.3m 可能值与 e 的 700000 个可能值之间的交集之间存在巨大差异,一方面减少了 1000000 倍,另一方面,1.7m 记录.
我无法进行其他预处理来生成例如 e、n 或它们的交集的子集。
result = ""
cp = True
ep = 0
while ep < 700000: #700000
np = 0
while np < 1300000: #1300000
df2 = df1[(df1["e"] >= ep) & (df1["e"] < ep + 1000) & (df1["n"] >= np) & (df1["n"] < np + 1000)]
if not df2.dropna().empty:
df3 = df2[df2.o== df2.o.min()]
df4 = df3.drop(columns = ["e", "n", "o"])
z = df4.to_string(header = cp)
result = result + "\n" + z
cp = False
np += 1000
np = 0
ep += 1000
样本数据:
p e n o
15646 str0 134746.0 466842.0 421.283752
15643 str1 134229.0 466923.0 502.364410
15588 str2 134023.0 467007.0 685.986880
15645 str3 133142.0 467081.0 551.112511
15649 str4 132632.0 467511.0 132.457540
32508 str5 133995.0 607803.0 580.374017
32502 str6 133750.0 607900.0 471.699057
32509 str7 133462.0 607987.0 488.480296
32532 str8 134761.0 608314.0 320.494930
32526 str9 130148.0 608801.0 463.146845
@Błotosmętek 提出的使用 df_aux 的建议(但使用 while 循环,请参阅下面的讨论)取得了巨大的改进。
解决方案
在代码的第 5 行中,您显然是从 中选择记录的子集df1
,其中的值e
在当前范围ep
内ep+1000
- 但您每次都在内部循环中执行此操作。将这部分移到外循环应该会大大加快速度。另一个优化是不删除列,df3
而只是选择列'p'
。我还冒昧地将您的 while 循环替换为 for 循环,以提高可读性。
result = ''
for ep in range(0, 700000, 1000):
df_aux = df2 = df1[(df1["e"] >= ep) & (df1["e"] < ep + 1000)]
for np in range(0, 1300000, 1000):
df2 = df_aux[(df_aux["n"] >= np) & (df_aux["n"] < np + 1000)]
if not df2.dropna().empty:
df3 = df2[df2.offset == df2.offset.min()]
z = df3["p"].to_string()
result += "\n" + z
请检查结果是否与您的原始代码相同。
推荐阅读
- python - 简单的for循环将系列合并到数据帧上的内存错误
- python - 熊猫 - 日期分组内的分箱
- java - NetBeans 8.2 看不到创建 Java 应用程序的选项
- webpack - webpack 仅编译,没有构建输出以检查退出代码
- reactjs - 更改使用 chrome 扩展做出反应的输入值
- c# - 具有统一 BorderThickness 的边框无法绑定 BorderBrush 颜色
- css - 为什么在使用响应式桌面、移动设备或平板电脑时,在 hr 上使用 margin left = 47% 会有不同的作用?
- javascript - 下载网站清单需要执行哪些必要步骤?
- google-chrome - 屏幕阅读器无法读出移动浏览器上的复选框标签
- go - 在 golang 中更新 grpc 的接收和发送消息大小