我注意到使用C++标准库方法std::ostream::write()时出现了以下行为。
为了缓冲数据,我正在使用以下C++ API。
这个代码可以很好地工作(使用strace实用程序进行验证),只要我们在文件流上写入的数据大小(datasize)不大于指定的缓冲区大小。
为了缓冲数据,我正在使用以下C++ API。
std::ofstream::rdbuf()->pubsetbuf(char* s, streamsize n)
这个代码可以很好地工作(使用strace实用程序进行验证),只要我们在文件流上写入的数据大小(datasize)不大于指定的缓冲区大小。
std::ofstream::write (const char* s, datasize n)
当写入的数据小于1023字节时(在此值以下,写入将被累积,直到缓冲区不再为空),但当要写入的数据大小超过1023时,缓冲区将不会被考虑,数据将被刷新到文件中。
例如,如果我将缓冲区大小设置为10KB,并每次写入约512字节,则strace将显示多个写操作已合并为单个写入操作。
writev(3, [{"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"..., 9728}, {"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"..., 512}], 2) = 10240 ( 10 KB )
writev(3, [{"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"..., 9728}, {"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"..., 512}], 2) = 10240
...
但是,当我每次写入1024字节(将缓冲区保持为10 KB)时,现在strace显示它没有使用缓冲区,并且每个ofstream::write调用都被转换为写系统调用。
writev(3, [{NULL, 0}, {"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"..., 1024}], 2) = 1024 ( 1KB )
writev(3, [{NULL, 0}, {"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"..., 1024}], 2) = 1024
...
我是否遗漏了任何C++ API调用或Linux优化参数?
std::flush
操作符,但它会强制刷新缓冲区,这与OP想要的相反。 - Sebastian Redl