在 CentOS(以及大多数 Linux 系统)上,优化 readdir(目录遍历)性能,通常不是优化 readdir 本身,而是从文件系统、目录结构、缓存和系统参数等方面入手。下面按常见场景给你系统性建议。
readdir 慢通常不是函数本身,而是以下原因:
强烈建议:
✅ 推荐做法:
data/
├── 00/
├── 01/
├── 02/
└── ff/
例如按 hash 分目录:
hash=$(echo -n "$filename" | md5sum | cut -c1-2)
mkdir -p data/$hash
CentOS 7/8/Stream 默认都是 XFS,对大目录支持比 ext4 更好。
df -T
如果不是 XFS,建议迁移。
编辑 /etc/fstab:
UUID=xxxx /data xfs noatime,nodiratime,allocsize=16m 0 0
说明:
noatime:不更新访问时间(非常重要)nodiratime:目录访问时间allocsize:减少碎片重新挂载:
mount -o remount /data
如果目录会反复遍历:
ls /data/bigdir >/dev/null
或:
find /data/bigdir -maxdepth 1 >/dev/null
✅ 效果:
readdir 基本无磁盘 IOreaddir + lstat 非常慢。
❌ 错误示例:
while (readdir) {
lstat();
}
✅ 如果只需要文件名,不要 stat。
getdents 而不是 readdirreaddir 是 glibc 封装,开销更大。
✅ 高阶优化(C/C++):
syscall(SYS_getdents, fd, buf, sizeof(buf));
opendir + readdir 的正确姿势DIR *dir = opendir(path);
struct dirent *entry;
while ((entry = readdir(dir))) {
// 避免频繁 malloc / string 操作
}
closedir(dir);
查看:
cat /proc/sys/fs/dentry-state
cat /proc/sys/fs/inode-state
一般不需要手动调,除非内存很大。
sysctl -w vm.vfs_cache_pressure=50
永久:
echo "vm.vfs_cache_pressure = 50" >> /etc/sysctl.conf
✅ 适合:
例如:
index.txt✅ 是否单目录文件过多?
✅ 是否使用 XFS?
✅ 是否开启 noatime?
✅ 是否频繁 stat?
✅ 是否可加目录缓存?
✅ 是否可拆分目录?
只要告诉我:
目录文件数量、文件系统、语言、使用场景