打开APP
userphoto
未登录

开通VIP,畅享免费电子书等14项超值服

开通VIP
c++ 连续的 std::cout<< xxx <<... 能不能保证是原子的?

不能。

C++的<<其实是函数调用的语法糖,它实际上等于调用了ostream.operator<<()。

普通的函数是无法链式调用的,因此C++强制要求ostream.operator<<返回另一个ostream。换句话说<<的函数原型是:

ostream ostream.operator<<(std::string s);

它的执行过程其实是:

ostream tempStream;

tempStream = std::cout.operator<<(a);

tempStream = tempStream.operator<<(b);

tempStream = tempStream.operator<<(c);

tempStream = tempStream.operator<<('\n');

这显然不可能是原子的。


大致看了下std::osyncstream的文档:

从文档描述看,它可能使用了scope_guard的实现思路。

也就是说,它的每次<<调用仍然不是原子的;但数据会在内部缓存、不会真的写出去。直到局部变量作用域结束、临时对象被销毁时,才会一次性的、原子的把之前缓存的信息写出去。

这在效果上,可以确保字符输出是原子的;但另一方面,如果用这个做日志的话,尤其是具名变量方式使用,它会导致日志延迟输出(不出作用域不会写盘)。这在一些要求严格的日志应用场景是不可接受的(比如银行之类、要求每个步骤严格落实到磁盘)。

而临时变量方式会好得多。因为它会在不再使用时第一时间被析构。

换句话说,它会在这行代码的分号处析构:

std::osyncstream(std::cout) << "Hello, " << "World!" << '\n';

这个行为显然更符合预期。

本站仅提供存储服务,所有内容均由用户发布,如发现有害或侵权内容,请点击举报
打开APP,阅读全文并永久保存 查看更多类似文章
猜你喜欢
类似文章
【热】打开小程序,算一算2024你的财运
第一章 深入浅出IO流
VC6.0中重载操作符函数无法访问类的私有成员
C++运算符重载(2)
std::endl 名字空间
string类实现(C++)
快速傅里叶变换C++递归算法实现
更多类似文章 >>
生活服务
热点新闻
分享 收藏 导长图 关注 下载文章
绑定账号成功
后续可登录账号畅享VIP特权!
如果VIP功能使用有故障,
可点击这里联系客服!

联系客服