You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用PyArrow处理超内存的Arrow IPC(Feather)文件?

处理超内存Arrow IPC(Feather)文件的实用方案

核心思路:别纠结限制内存映射长度,利用Arrow列存特性分治处理

PyArrow的内存映射默认是映射整个文件,但操作系统会按需加载磁盘页,不会一次性把整个文件塞进内存。你遇到的内存溢出,大概率是因为直接把数据转成了Pandas DataFrame(Pandas会把所有数据加载到内存),而非用Arrow的懒加载特性处理。下面是具体解决方法:


1. 分批次读取数据(推荐)

用pyarrow.dataset API按批次迭代读取,每次只处理一小部分数据,避免一次性加载全量:

import pyarrow.dataset as ds

# 加载Feather文件为dataset
dataset = ds.dataset("large_file.feather", format="feather")

# 创建扫描器,设置批次大小,还可指定过滤条件、需要的列
scanner = dataset.scanner(
    columns=["col1", "col3"],  # 只加载需要的列,进一步减少内存
    batch_size=10_000  # 每次读取1万行,可根据内存调整
)

# 迭代处理每个批次
for batch in scanner.to_batches():
    # 优先用Arrow的Batch原生处理,避免转Pandas
    process_batch(batch)
    
    # 若必须转Pandas,处理完及时释放内存
    df = batch.to_pandas()
    process_df(df)
    del df

2. 只加载需要的列

不管用read_feather还是dataset,都可以通过columns参数指定要读取的列,避免加载无关列占用内存:

import pyarrow.feather as feather

# 只读取指定列,返回Arrow Table(懒加载,内存占用低)
table = feather.read_feather("large_file.feather", columns=["col1", "col2"])

# 按列或分块处理,而非转成全量DataFrame
for column in table.columns:
    process_column(column)

3. 正确使用内存映射的姿势

如果直接用MemoryMappedFile,记住:Arrow的Table基于内存映射时是懒加载的,只有访问具体数据时才会加载对应页。尽量用Arrow原生接口处理,不要直接转Pandas:

import pyarrow.ipc as ipc
from pyarrow import MemoryMappedFile

with MemoryMappedFile("large_file.feather", "r") as mmf:
    reader = ipc.open_file(mmf)
    # 按列读取
    col1 = reader.get_column_by_name("col1")
    # 分块处理列数据
    for chunk in col1.chunks:
        process_chunk(chunk)

为什么默认内存映射会溢出?

PyArrow的read_feather默认返回Arrow Table,这个Table本身不会加载全量数据到内存,但如果你调用table.to_pandas(),Pandas会把所有数据复制到内存中,这才是溢出的核心原因。所以尽量在Arrow原生格式下处理数据,必要时再转小批次的Pandas DataFrame。


内容的提问来源于stack exchange,提问作者Matt Robin

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.10 00:40:00