什么是最接近 std::atomic<std::vector> 的东西?

What's the closest thing to `std::atomic<std::vector>`?

我是 std::atomic 的新手。如果我理解正确的话,这样的变量一次不能被多个线程访问,线程如果试图这样做就被强制轮流访问。

我有一个 std::vector<std::string> 需要使其成为原子。最简单、最万无一失的方法是什么?

我有 2 个线程。一个偶尔将字符串推入向量,另一个线程不断读取然后从向量中删除所有字符串。

线程 1,DLL 1

// about one per second
// this function is exported from DLL 2
myVector.push_back(myString);

线程 2,DLL 2

 while (true) {
        if (myVector.size() > 0) {
            std::string myString = myVector.at(0);
            std::string myCopy;
            myCopy.assign(myString);
            myVector.erase(myVector.begin());
        }
}

拥有 "simplest, most fool-prof thing" 的目标和处理复杂数据结构的目标 atomic 相互矛盾。

追求目标的一种方法是采用基于锁的方法。评论暗示了这一点。通常,基于锁的方法有其自身的注意事项(存在死锁和饥饿),但对于您的情况,它会起作用,但可能仍然不是最佳选择。

您需要的似乎是生产者-消费者队列。单一生产者,单一消费者。


如果你有高性能的期望,应该是无锁的,基于ring-buffer的。

boost::lockfree::spsc_queue 是一种可能的实现方式。还有其他实现。

此外,您可能希望避免分配字符串并使用 boost::lockfree::spsc_queue<char>,并使用 [=13=] 分隔字符串。

如果您想要更快的速度,您可能有自己的实现,并针对您的场景进行了优化。


但是如果你说 "One occasionally pushes strings into the vector",而 occationally 意味着 不经常,你可能需要基于锁的队列。

Boost.Thread 有 Synchronized Queues -- EXPERIMENTAL。还有其他实现。

这样代替直接使用mutex/condition_variable的好处是不用自己写同步,所以真正满足"simplest, most fool-prof thing"


我实际上在我的程序中实现了混合方法。当它需要等待时,它变成基于锁的,否则是无锁的。我还没有看到很好的开源实现,但我想看看。