A bounded multi-producer multi-consumer concurrent queue written in C++11.
It's battle hardened and used daily in production:
It's been cited by the following papers:
MPMCQueue<int> q(10);
auto t1 = std::thread([&] {
int v;
q.pop(v);
std::cout << "t1 " << v << "n";
});
auto t2 = std::thread([&] {
int v;
q.pop(v);
std::cout << "t2 " << v << "n";
});
q.push(1);
q.push(2);
t1.join();
t2.join();
MPMCQueue<T>(size_t capacity);
Constructs a new MPMCQueue
holding items of type T
with capacity
capacity
.
void emplace(Args &&... args);
Enqueue an item using inplace construction. Blocks if queue is full.
bool try_emplace(Args &&... args);
Try to enqueue an item using inplace construction. Returns true
on
success and false
if queue is full.
void push(const T &v);
Enqueue an item using copy construction. Blocks if queue is full.
template <typename P> void push(P &&v);
Enqueue an item using move construction. Participates in overload
resolution only if std::is_nothrow_constructible<T, P&&>::value == true
. Blocks if queue is full.
bool try_push(const T &v);
Try to enqueue an item using copy construction. Returns true
on
success and false
if queue is full.
template <typename P> bool try_push(P &&v);
Try to enqueue an item using move construction. Participates in
overload resolution only if std::is_nothrow_constructible<T, P&&>::value == true
. Returns true
on success and false
if queue
is full.
void pop(T &v);
Dequeue an item by copying or moving the item into v
. Blocks if
queue is empty.
bool try_pop(T &v);
Try to dequeue an item by copying or moving the item into
v
. Return true
on sucess and false
if the queue is empty.
ssize_t size();
Returns the number of elements in the queue.
The size can be negative when the queue is empty and there is at least one reader waiting. Since this is a concurrent queue the size is only a best effort guess until all reader and writer threads have been joined.
bool empty();
Returns true if the queue is empty.
Since this is a concurrent queue this is only a best effort guess until all reader and writer threads have been joined.
All operations except construction and destruction are thread safe.
Enqeue:
Dequeue:
References:
Testing concurrency algorithms is hard. I'm using two approaches to test the implementation:
boost::lockfree::queue
and othersstatic_assert
if availablestd::hardware_destructive_interference_size
if available[[nodiscard]]
attributesThis project was created by Erik Rigtorp <[email protected]>.