0

我有 185 个数据文件,总共包含 3000 万行。每两个有两列;我想用作索引的单个 int 和 512 个 int 的列表。

所以它看起来像这样

IndexID Ids
1899317 [0, 47715, 1757, 9, 38994, 230, 12, 241, 12228...
22861131    [0, 48156, 154, 6304, 43611, 11, 9496, 8982, 1...
2163410 [0, 26039, 41156, 227, 860, 3320, 6673, 260, 1...
15760716    [0, 40883, 4086, 11, 5, 18559, 1923, 1494, 4, ...
12244098    [0, 45651, 4128, 227, 5, 10397, 995, 731, 9, 3...

数据太大而无法加载到内存中,但我想使用索引列表一次检索几百行。

我从这条评论中得到了使用 Parquet 的建议。 将 pandas 数据帧或 2d numpy 数组保存到 h5py 中的最有效方法,每行一个单独的键,使用一列

我一直在看官方的 parquet python guide

https://arrow.apache.org/docs/python/parquet.html

快速镶木地板指南

https://fastparquet.readthedocs.io/en/latest/api.html

但我似乎找不到任何方法来使用索引检索行,以及表是否存储在磁盘上,或者是否全部加载到内存中。

这可能吗?如果是这样,我将如何做这样的事情?

例如

ParquetTable[22861131, 15760716]

[0, 48156, 154, 6304, 43611, 11, 9496, 8982, 1... [0, 40883, 4086, 11, 5, 18559, 1923, 1494, 4, ...

4

1 回答 1

1

Parquet 是一种列式数据存储,不适合您的用例。如果您的目标是存储太大而无法放入内存的数据,但仍然能够一次检索行以进行处理,我建议您使用数据库。

最简单的数据库是sqlite3,它内置在 Python 本身中。Sqlite 数据库存储为文件,而不需要您设置数据库系统。

在我们继续之前,您需要将您的列表列分解为 512 列,以 (1) 使它们更易于使用,以及 (2) 我不认为数据库系统天生就支持列表。

这是一个关于如何转储数据并检索所需行的最小示例:

# Creating sample data to work on
import pandas as pd
import numpy as np

df = pd.DataFrame(
        data=np.random.randint(low=1, high=1000, size=(1000, 3)),
        columns=['a', 'b', 'c'],
        index=pd.Series(range(1000), name='IndexID')
)

import sqlite3

# Write dataframes to database
with sqlite3.connect('sqlite.db') as conn:
    df.to_sql('data', con=conn, if_exists='append')

上面的代码将 的内容转储df到当前工作目录中的 sqlite 数据库中,名为sqlite.db. 注意调用if_exists中的选项to_sqlreplace如果要覆盖现有数据库,则需要将其更改为。

当您想从同一工作目录中检索特定行时,可以运行以下命令。下面的示例检索第 200 到第 210 个索引:

# How to read from database
with sqlite3.connect('sqlite.db') as conn:
    # `rowid` is a keyword in sqlite queries to represent the index
    query = "SELECT * FROM data WHERE rowid BETWEEN %d AND %d" % (200, 210)
    subset = pd.read_sql(query, con=conn)

print(subset)
# This prints the following
#     IndexID    a    b    c
# 0       199  704    3  423
# 1       200  590  299  767
# 2       201   45  953  560
# 3       202  237  662  746
# 4       203  123  920  275
# 5       204  453   10  370
# 6       205   35  628  602
# 7       206  957  465  735
# 8       207  602  810  154
# 9       208  927  796  352
# 10      209  969  130  217

有关在 sqlite3 和 pandas 之间移动数据的更多信息,我建议阅读此https://www.dataquest.io/blog/python-pandas-databases/How to open and convert sqlite database to pandas dataframe

于 2020-05-10T10:48:29.353 回答