在 Debian(或其他 Linux)上 readdir() 慢,通常不是 readdir 本身慢,而是目录本身、文件系统、或底层存储的问题。下面按「常见原因 → 排查方法 → 解决办法」给你一套实战思路。
time 简单测time ls -1 /path/to/dir >/dev/null
如果几千个文件就卡几秒,基本就是目录或 IO 问题。
strace 看系统调用strace -e trace=file ls /path/to/dir
重点看:
openatgetdents64stat如果 getdents64 很慢 → 文件系统/存储问题
如果 stat 很多 → 程序在额外获取文件信息
readdir 是线性扫描。
✅ 解法:
a/ab/abcd.txt
很多程序:
while ((de = readdir(dir))) {
stat(de->d_name, &st); // 慢点在这
}
✅ 解法:
readdir() + d_type(仅 ext4/xfs 支持)statx() / getdents + 批量处理opendir + scandir(排序但可控)readdir 在网络 FS 上非常慢。
✅ 解法:
readdir 次数actimeo)ls -l 远程目录getdents 需要读目录 inode。
✅ 解法:
| FS | readdir 表现 |
|---|---|
| ext4 | ✅ 好 |
| xfs | ✅ 非常好 |
| btrfs | ⚠️ 大目录慢 |
| overlayfs | ⚠️ 慢(Docker 常见) |
✅ 解法:
✅ 检查:
dmesg | grep error
✅ 修复:
fsck -f /dev/sdX
getdents64 直接读openat() + fd 避免路径解析readdir + stat 混用os.scandir() # 比 os.listdir 快很多
避免:
for f in *; do stat $f; done
改用:
find . -maxdepth 1
如果你愿意,可以告诉我:
我可以直接给你针对性的优化方案或代码改法。