我有大约 20 个特征和数百万个观察值(行)的表。
我需要在这个表上创建模型,但是,因为它很大,像随机森林或 XGB 这样的训练模型需要很长时间。我主要使用 python 在 Jupyter 实验室服务器上使用 scikit-learn 和 XGBoost 包,当数据帧非常大时,我正在努力解决这个问题。另外值得一提的是,我有 Windows(不是 Linux)。
我的问题是针对比我有更多经验的人:你如何处理巨大的数据框?当数据如此之大时,是否有更好的软件包或平台可供使用?
我有大约 20 个特征和数百万个观察值(行)的表。
我需要在这个表上创建模型,但是,因为它很大,像随机森林或 XGB 这样的训练模型需要很长时间。我主要使用 python 在 Jupyter 实验室服务器上使用 scikit-learn 和 XGBoost 包,当数据帧非常大时,我正在努力解决这个问题。另外值得一提的是,我有 Windows(不是 Linux)。
我的问题是针对比我有更多经验的人:你如何处理巨大的数据框?当数据如此之大时,是否有更好的软件包或平台可供使用?
在笔记本电脑上对 20 个功能的一百万次观察应该是非常易于管理的,即使速度有点慢。非常大的数据集的云计算成本高得惊人,而且除非并且直到您有良好的并行化,否则几乎没有好处或根本没有好处。我建议保留该选项作为您的最后手段。
对于最初的数据探索和实验,我建议您对数据进行抽样。花几分钟谷歌搜索“数据采样”将为您节省大量时间和精力。只有当你的样本得到合理的结果时,你才应该考虑将你的方法应用于更大的数据集。
还要认真考虑降维,像 PCA 这样的方法在这里会很有帮助。如果您还没有这样做,对您的特征进行相关性分析可能会帮助您消除不太有用的特征。
您可以在这里做两件事:
1.) 使用像 Dask 这样的库来加速你的数据预处理。这是链接
2.) 使用 Azure、AWS 或 GCP 等云计算服务。我不知道其他两个,但我在 Azure 上工作过,它为实现数据科学解决方案提供了很多选项。您可以获得 Auto-ML、Azure Designer、Python ML SDK 等选项。
所以这取决于你。如果您的限制是您的计算设置,那么使用 Dask 帮助不大,您应该选择云服务。但如果不是这样,那就去 Dask。
使用例如 pandarallel等在单个(多 cpu)机器上并行化您的分析, 或者如果问题不适合单台机器,则使用 scala/spark/hadoop 破产。
这个问题问得好。我将它分为两部分:
在那个规模上,像 Pandas 这样的库通常不是一个好选择。一个简单的 pd.read_csv 可能会导致内存不足错误。选项是:
数据表:https ://github.com/h2oai/datatable - 可以快速高效地读取和处理大型数据集
DASK( https://dask.org/ ) - 使用并行处理本地扩展 pandas 工作流的框架。如果您曾经使用过 Spark,这将很容易习惯,因为它在概念上很相似
NVIDIA 的 Rapids 框架https://rapids.ai/ - 如果您使用 GPU 是另一个不错的选择。最好的部分是它几乎等同于所有适用于大数据的 Scikit 方法。这可能是您正在寻找的东西
最后,最好将数据集转换为处理速度更快的格式。有多种格式可以存储数据集。但是请注意,并非所有库都支持所有格式。一些好的格式是 - 羽毛、hdf5、镶木地板、松鸦、泡菜。好消息是 Pandas 支持所有这些格式 - https://pandas.pydata.org/pandas-docs/stable/user_guide/io.html
现在进入第二部分,即模型的实际处理。这里没有简单的解决方案,因为这取决于手头的具体情况。如果您能够通过聚类或其他方法有效地对数据子集进行采样(基于您在使用完整数据时在 EDA 步骤中学到的知识......),那么没有什么比这更好的了。如果您必须使用完整数据,那么您可以选择像 Rapids 这样的库,正如我所提到的,它支持 Scikit 更大规模支持的许多模型。
您还可以采取一些较小的行动来帮助:
重新访问所有数据类型并转换为占用空间较小的数据类型(例如 float64 → float32、int64 → int8 等,但要小心操作)。检查内存效率不高的“对象”数据类型,然后再次转换为更轻的数据类型(当然这取决于对象所持有的内容)。虽然这听起来微不足道,但相信我在实践中,这有效
在处理中使用矢量化操作。不要使用循环。大多数时候它们是不需要的。向量化器在底层 C 代码上运行时速度非常快 - https://realpython.com/numpy-array-programming/
仔细观察内存吸收操作。您可以使用这样的简单代码
`
mem_details = []
def memory_ckpt():
mem_details.append(psutil.virtual_memory()[3])
mem_used_step = mem_details[-1] - mem_details[-2] if len(mem_details) > 1 else 0
mem_used_total = mem_details[-1] - mem_details[0] if len(mem_details) > 1 else 0
if mem_used_step > 50000000:
print('Mem Warning, High memory usage step:', round(mem_used_step/1073741824, 2), ' GB\n')
elif mem_used_step < -50000000:
print('Mem Note, High memory release step:', round(mem_used_step/1073741824, 2), ' GB\n')
if mem_used_total > 6000000000:
print('Mem Warning, High memory usage cumulatively by the code in the kernel:', round(mem_used_total/1073741824,2), ' GB\n')
print('Total Memory used at start of kernel before line 1:', round(mem_details[0]/1073741824,2), ' GB\n')
print('Total Memory used as of this step:', round(mem_details[-1]/1073741824,2), ' GB\n')
`
在每个主要处理步骤之前和之后调用上面的 memory_ckpt() 以查看您在哪里使用内存,这将帮助您更好地设计代码(请记住根据您的机器内存调整函数中的内存检查点)
作为最后的手段,您可能需要迁移到大数据平台 - Scala-Spark 上的 XGBoost4j、带有 H2O.ai 的 XGBoost、Amazon SageMaker 等