我有以下代码,
#include <string>
#include <thread>
#include <memory>
#include <condition_variable>
#include <mutex>
#include <deque>
#include <iostream>
#include <vector>
#include "third_party/concurrentqueue.h"
struct Dummy {
std::string name_;
};
class Consumer {
public:
Consumer() {
is_running_ = true;
data_thread_ = std::unique_ptr<std::thread>(new std::thread(&Consumer::listening, this));
}
void push(std::shared_ptr<Dummy> frame)
{
nice_queue.enqueue(frame);
}
virtual void listening() {
while (is_running_) {
std::shared_ptr<Dummy> frame;
if (nice_queue.try_dequeue(frame)) {
std::cout << frame->name_ << std::endl; //<--- is here a possible race condition as there is no memory fence
}
}
}
std::unique_ptr<std::thread> data_thread_;
moodycamel::ConcurrentQueue<std::shared_ptr<Dummy>> nice_queue;
std::atomic<bool> is_running_;
};
class Producer {
public:
Producer(std::shared_ptr<Consumer> consumer)
:consumer_(consumer){}
void send(std::shared_ptr<Dummy> frame) {
consumer_->push(frame);
}
protected:
std::shared_ptr<Consumer> consumer_;
};
int main() {
std::shared_ptr<Consumer> consumer = std::make_shared<Consumer>();
Producer prod(consumer);
for(int i =0; i<100; i++){
auto item = std::make_shared<Dummy>();
item->name_ = std::to_string(i);
prod.send(item);
}
}
我的问题是,如代码所示,
Producer
将一个项目发送到Consumer
以在另一个线程中处理,因此两件事严格地相继发生,但由于没有内存栅栏,是否有可能当 Consumer
处理该项目时,它看不到该项目的最终版本,因此具有未定义的行为?
同步发生在
moodycamel::ConcurrentQueue
的幕后。
正如名称(和文档)所示,它是一个线程安全队列。因此可以同时从不同线程写入和读取。
您发送
shared_ptr
的事实不会对这里产生任何影响。