【问题标题】:Is C++ std::queue safe if there are a pushing-only thread and a popping-only thread?如果存在仅推送线程和仅弹出线程,C++ std::queue 是否安全?
【发布时间】:2013-07-16 02:50:07
【问题描述】:
我想知道这种情况是否(线程)安全。
有一个线程只推送到 std::queue。
还有另一个线程只从 std::queue 中弹出。
由于队列是否为空,都是线程安全管理的,后面的线程不会弹出失败。
你能帮帮我吗?
谢谢。
【问题讨论】:
-
我认为即使是读读情况也不安全,因为你所做的不会完全阅读(检查大小,top(),pop()(肯定有些写在这里)) .您应该使用互斥锁 (std::mutex) 之类的保护措施,或者使用 Boost.Lockfree 中的保护措施会更好。
标签:
c++
multithreading
thread-safety
queue
【解决方案1】:
我相信答案是否定的。
标准说(§23.2.2/1):
为了避免数据竞争 (17.6.5.9),实现应将以下函数视为 const:begin、end、rbegin、rend、front、back、data、find、lower_bound、upper_bound、equal_range、at 和,除了在关联或无序关联容器中,operator[]。
至少正如我所解释的那样(和Herb Sutter seems to agree),这意味着这些函数(以及仅那些函数)可以被视为“线程安全”。 Push 和 pop 不在列表中,所以你不能假设它们是线程安全的。
我还要补充一点,即使弹出实际上也会写入数据——当您从容器中弹出一个项目时,需要更新容器的大小,因此推送和弹出都会写入。当不止一个线程在写时,你需要做一些事情来确保一次只有一个线程在写。
总结一下:抱歉,没有。