在 StreamSink
类中,成员变量 _write_occurred
的作用是 跟踪自上次刷新(Flush)以来是否有写入操作发生,其核心目的是 优化 I/O 性能。以下是详细解析:
_write_occurred
的作用write_log
方法(日志写入)被调用时,_write_occurred
会被设为 true
;flush_sink
方法(主动刷新)被调用时,仅在 _write_occurred
为 true
时执行实际的 fflush
操作,随后将其重置为 false
。fflush
(系统调用),减少 I/O 开销。flush_sink
但无新日志写入,只有第一次会真正执行 fflush
。void write_log(..., std::string_view log_statement) override {
// ... 写入日志到文件
safe_fwrite(...); // 实际写入操作
_write_occurred = true; // 标记有写入发生
}
write_log
即标记为 true
。void flush_sink() override {
if (!_write_occurred || !_file) {
return; // 无写入或文件未打开时直接返回
}
flush(); // 执行实际刷新
}
void flush() {
_write_occurred = false; // 重置标记
fflush(_file); // 系统调用刷新缓冲区
}
fflush
,避免无意义刷新。场景 | 无 _write_occurred |
有 _write_occurred |
---|---|---|
高频写入 | 每次 flush 触发 fflush ,I/O 压力大 |
仅在必要时触发 fflush ,减少系统调用 |
低频写入 | 多余的 fflush 浪费 CPU 周期 |
无写入时跳过 fflush ,节省资源 |
_file
变为 nullptr
),flush_sink
会直接返回,避免操作无效指针。// 连续写入多条日志
sink.write_log(...); // _write_occurred = true
sink.write_log(...); // _write_occurred = true
sink.flush_sink(); // 实际刷新,重置 _write_occurred = false
sink.flush_sink(); // 直接返回(无新写入)
// 定时器每 1 秒触发刷新
void on_timer() {
sink.flush_sink(); // 仅当 1 秒内有新写入时刷新
}
fflush
的成本fflush
会触发用户态到内核态的上下文切换,频繁调用可能成为性能瓶颈。_write_occurred
减少 fflush
次数,在 数据安全性(及时持久化)和 性能 之间取得平衡。_write_occurred
是一个轻量级的状态标志,通过简单的布尔值跟踪写入状态,实现了:
它是高性能日志库中常见的优化手段之一,尤其适用于需要平衡实时性和吞吐量的场景。
感触:对于一些好的三方库,还是有很多值得我们学习借鉴的知识点的,需要我们多想多思考多问一个为什么
【技术人的鼓励】❤️ 如果这篇文章对您有帮助,欢迎点击打赏按钮支持博主!您的鼓励是我持续输出优质技术内容的动力,哪怕只是1元也足以让我感受到这份珍贵的认可。