【问题标题】:Reading a large table with millions of rows from Oracle and writing to HDF5从 Oracle 读取具有数百万行的大表并写入 HDF5
【发布时间】:2014-01-04 07:01:15
【问题描述】:

我正在使用具有数百万行和 100 多列的 Oracle 数据库。我正在尝试使用带有索引的某些列的 pytables 将此数据存储在 HDF5 文件中。我将在 pandas DataFrame 中读取这些数据的子集并执行计算。

我尝试了以下方法:

使用实用程序将表下载到 csv 文件中,使用 pandas 逐块读取 csv 文件,并使用 pandas.HDFStore 附加到 HDF5 表。我创建了一个 dtype 定义并提供了最大字符串大小。

但是,现在当我尝试直接从 Oracle DB 下载数据并通过 pandas.HDFStore 将其发布到 HDF5 文件时,我遇到了一些问题。

pandas.io.sql.read_frame 不支持分块读取。我没有足够的 RAM 来先将整个数据下载到内存中。

如果我尝试将cursor.fecthmany() 与固定数量的记录一起使用,则读取操作在未编制索引的数据库表中需要很长时间,我必须读取日期范围内的记录。我正在使用DataFrame(cursor.fetchmany(), columns = ['a','b','c'], dtype=my_dtype) 但是,创建的 DataFrame 总是推断 dtype 而不是强制执行我提供的 dtype(与 read_csv 坚持我提供的 dtype 不同)。因此,当我将此 DataFrame 附加到已经存在的 HDFDatastore 时,例如存在类型不匹配。一个 float64 可能会在一个块中解释为 int64。

如果你们能提出你的想法并为我指明正确的方向,不胜感激。

【问题讨论】:

  • 您当前的方法(使用 csv)和 dtype 校正是正确的。 SQL 将在 0.14 中获得重大更新(0.13 即将发布)。所以不幸的是 dtype 推理/分块不可用。不过欢迎 PRS!看到这个问题:github.com/pydata/pandas/issues/4163
  • 我建议删除 Oracle 标记,除非您在 Oracle 方面遇到任何问题。
  • 您应该要求您的 dba 将表转换为范围分区对象,之后应该很容易通过分区访问
  • 如果您不将所有数据导出到单个 CSV 文件,而只是将该文件分成几位,这难道不能解决问题吗?如果您必须定期执行此工作,这也将减少空间需求和运行时间,如果 Oracle 导出一个接一个地导出一个小 CSV,而 HDF5 进程并行导入它们,删除完成的文件...

标签: python pandas hdf5 pytables


【解决方案1】:

好的,所以我对 oracle 数据库没有太多经验,但这里有一些想法:

您从 oracle 访问任何特定记录的时间都很慢,因为缺少索引,而且您希望数据按时间戳顺序排列。

首先,你不能为数据库启用索引?

如果你不能操作数据库,你大概可以请求一个只包含每行的有序唯一 ID 的搜索结果?

您可能会将这些数据存储为唯一 ID 的单个数组,并且您应该能够适应内存。如果您为每个唯一键(保守估计,包括开销等)允许 4k,并且您不保留时间戳,因此它只是一个整数数组,它可能会为 300 万条记录占用大约 1.1GB 的 RAM。这不是一个完整的堆,大概您只想要一个小窗口的活动数据,或者您正在逐行处理?

创建一个生成器函数来完成所有这些。这样,一旦你完成迭代,它应该释放内存,而无需删除任何东西,而且它还使你的代码更容易遵循,并避免使你的计算循环的实际重要逻辑膨胀。

如果您无法将其全部存储在内存中,或者由于某些其他原因这不起作用,那么您能做的最好的事情就是计算出您可以在内存中存储多少。您可以将作业拆分为多个请求,并在最后一个请求完成后使用多线程发送请求,同时将数据处理到新文件中。在您要求返回数据之前,它不应该用完内存。尝试找出延迟是因为请求得到满足,还是因为数据正在下载。

听上去,您可能正在抽象数据库,并让 pandas 发出请求。可能值得看看它是如何限制结果的。您应该能够请求所有数据,但一次只能从数据库服务器加载一行结果。

【讨论】:

    【解决方案2】:

    好吧,目前唯一实用的解决方案是直接使用 PyTables,因为它是为内存不足操作而设计的......这有点乏味但还不错:

    http://www.pytables.org/moin/HintsForSQLUsers#Insertingdata

    另一种使用 Pandas 的方法在这里:

    "Large data" work flows using pandas

    【讨论】:

      猜你喜欢
      • 2016-08-22
      • 2011-01-04
      • 1970-01-01
      • 2018-12-21
      • 2022-07-07
      • 2016-08-22
      • 1970-01-01
      • 2021-06-14
      • 2017-11-26
      相关资源
      最近更新 更多