2026-10-31·par Sijie Wang

small-files

Small files: metadata cost per file, three costs, merge at write time, container formats, HAR, CombineFileInputFormat, and why adding DataNodes does not help.

小文件:元数据账单,和四种少付它的办法

动机就是元数据算术。 账在 block-size-and-metadata-math 里:文件再小,也至少一个文件节点加一块,决定成本的是文件个数,不是数据量。100 万个 1KB 文件的元数据,远多于 1 个 1GB 文件,而数据量只有后者的千分之一。

贵在三处。 第一是内存:NameNode 账本随文件个数长,极端时一台机器根本装不下。第二是启动:FsImage 加载和块报告吸收都随个数变慢。第三是处理:读一个小文件也要走全套流程——问 NameNode、找 DataNode、建连接——这套 overhead 比几 KB 数据本身还大。跑 MapReduce 时,一个小文件起一个 mapper,调度开销比计算还大。

四种少付的办法。 第一,写入端合并:攒一批再写一个大文件,别一个记录一个文件。这是治本,后面三条都是给已经产生的小文件治标。第二,容器格式:SequenceFile、Avro、Parquet 把很多条记录装进一个大文件,记录级可读、可切分,文件个数一下下来,记录访问还在。第三,HAR 归档:Hadoop Archive 把很多小文件打包成几个大文件加索引,读起来透明——但打包后不能改,所以 HAR 只适合冷的、定型的数据。第四,任务时合并 split:CombineFileInputFormat 把很多小 split 合成一个任务,mapper 数下来了,文件本身不用动。

什么帮不上。 加 DataNode 对 NameNode 一点用没有:瓶颈是账本,DataNode 存的是数据,不是账本条目。账本的扩容答案是 federation,而且即使那样也只在小文件摊到多个命名空间时才有用:全堆在一个命名空间里的小文件,照样炸掉那个 NameNode。先合并,再 federation。

à propos de cette entrée

L'une des entrées de wiki de sijie. L'IA sur ce site est fondée sur le même corpus et répond à la voix de sijie, avec citations revenant à des entrées comme celle-ci — répondre coûte argent à sijie, donc cela attend derrière un code : entrer un code d'accès →