我正在尝试使用 DuckDB 将 30 个 CSV 文件(大约 12Gb 未压缩和 3000 万行)读取到单个 Parquet 文件中。我今天已经升级到最新版本0.10.0了。
我的每一个 CSV 都是标准化的,因此我能够预先定义列名称和类型,并将其作为我的查询的一部分完成
COPY (SELECT * FROM read_csv('*.csv',
delim = ',',
header = false,
parallel = true,
auto_detect = false,
columns = {
'UPRN': 'BIGINT',
'UDPRN': 'INT',
'CHANGE_TYPE': 'VARCHAR(1)',
70 more attributes))
TO 'output.parquet' (FORMAT 'parquet', COMPRESSION 'zstd', ROW_GROUP_SIZE 100000)
每次运行此程序时,我都会遇到内存不足错误。
因此我尝试将 CSV 数据加载到持久的本地数据库中,然后进行复制导出
COPY table TO 'output.parquet' (FORMAT 'parquet', COMPRESSION 'zstd', ROW_GROUP_SIZE 100000)
同样的内存不足错误消息。
Error: Out of Memory Error: failed to allocate data of size 4.2 MiB (13.9 GiB/13.9 GiB used)
我阅读了最近的发行说明,有一个新的临时内存管理器,我可以使用它并设置内存限制
PRAGMA memory_limit = '10GB';
这似乎确实使加载更加稳定,但对 Parquet 导出没有影响。
我使用的是具有 32Gb RAM 的 Windows 笔记本电脑,使用最新的 DuckDB CLI。
我确信还有其他 Python 类型的方法可以做到这一点,但我更愿意坚持使用 DuckDB,因为我在另一个进程中使用它,它是一个很棒的工具!
尝试关闭preserve_insertion_order选项:
SET preserve_insertion_order = false;
此外,新的“拉取请求”将有助于减少 Parquet 导出的内存消耗。在撰写本文时尚未合并,但可能会成为几周后即将发布的 DuckDB 版本的一部分。