Pandas 가 메모리에서 죽는 시점
월별 운영 로그를 한 번에 분석하려다 2GB VM 의 OOM Killer 와 만났다.
월별 운영 로그 파일 3개 (각 1.2GB) 를 한 번에 합쳐서 분석하려 했다.
df = pd.concat([pd.read_csv(f) for f in files])
3분 후 SSH 세션이 끊겼다. dmesg 를 보니 Out of memory: Killed process — Pandas 가 메모리 12GB 까지 부풀어 있었다. 2GB VM 에서.
CSV 가 메모리에서 왜 5배가 되나
- CSV 의 숫자 컬럼은 기본
int64(8 byte/cell) — 원본 텍스트 “1” (1 byte) 대비 8배 - 문자열 컬럼은 Python object 로 들어감 — 한 글자에 ~50 byte
pd.concat의 임시 버퍼가 한 번 더
해결
세 가지를 같이 했다.
dtype명시:read_csv(f, dtype={'count': 'int32', 'kind': 'category'})- 청크 단위 처리:
read_csv(f, chunksize=100_000)→ 청크 별로 집계 → 마지막에 concat - 필요한 컬럼만 읽기:
usecols=['ts', 'kind', 'count']
메모리 사용량이 12GB → 380MB.
더 큰 교훈
처음부터 DuckDB 를 썼다면 이 글이 없었을 거다.
import duckdb
df = duckdb.sql("""
SELECT date_trunc('day', ts) d, kind, sum(count)
FROM read_csv('logs/*.csv')
GROUP BY 1, 2
""").df()
같은 작업이 메모리 200MB, 9초. Pandas 로 청크 처리한 380MB · 47초 와 비교가 안 된다.
다음에는 다르게 할 한 가지
CSV 파일이 1GB 를 넘는 순간 Pandas 의 직관적인 syntax 를 포기한다. DuckDB 의 SQL 한 줄이 Pandas 의 청크 처리보다 항상 더 단순하다.
🛒 이 글과 어울리는 추천 상품
위 링크는 쿠팡파트너스 활동의 일환이며, 일정액의 수수료를 제공받을 수 있습니다.