跳到正文

IO

共 2 篇 · 全部标签

瓶颈定位与优化次序:先判是哪一类(IO / CPU / 锁 / 数据布局),再决定动谁

汇总本专栏已实测的数字给出次序:直读随机 4 KB 是缓冲读法的 10.5 倍(75.64 vs 7.19 µs/次),把队列深度从 1 加到 16 又能把单价从 68.40 压到 13.16 µs——**同一个 IO 瓶颈,"换访问方式"值 10 倍、"加并发"值 5 倍**; 每行 `fflush` 是 1MB 缓冲的 31 倍(8195 ns/行),而把全局锁换成每线程私有缓冲是 8.5 倍(811.6 → 95.6 ns/行); 一次条件变量唤醒 11.35 µs 等于 186 次原子自旋交接(61 ns);201 个文件的编译全量 34.1 s,`-j8` 只买到 2.63 倍, 而"改一个文件别全量重编"值 14.1 倍——**依赖图比并行度便宜**;数据库那条加了两个索引反而慢 6.0 倍 (9.653 → 57.783 ms)、换成覆盖索引才回到 3.288 ms——**同一个"优化动作"可以是反向的**。 本文不新增任何测量,只做一件事:把这些数字排成一个可执行的判断顺序。

IO 栈、页缓存与异步 IO

实测:同一个 128 MB 文件,缓冲随机 4 KB 读中位 7.19 微秒/次、FILE_FLAG_NO_BUFFERING 同请求 75.64 微秒/次(10.5 倍);队列深度从 1 加到 16 把直读单价从 68.40 微秒压到 13.16 微秒,再加到 64 反而回落到 18.14。NO_BUFFERING 的三条约束里,缓冲区与长度不当会当场报 87(参数错误),而偏移不对齐是 SetFilePointerEx 悄悄失败——返回 0、文件位置不动,随后的 WriteFile 照样返回成功、写的却是上一个位置 (请求 100、落在 0,字节级取证见正文)。FlushFileBuffers 第一次 64 MB 收 28.63 毫秒、第二次只 0.057 毫秒;写完关掉句柄闲置 3 秒,脏页仍在。映射视图写 4 KB 首遍 1.72 微秒/页、第二遍 0.18 微秒,同一批偏移 走 WriteFile 要 21.86 微秒。同步句柄上 ReadFileEx 投 3 次完成例程只交付 1 次,而 SleepEx(1,TRUE) 一次真实阻塞 15.2 毫秒。