Mpsc channels vs Arc<Mutex<VecDeque<_>>>

Suppose we have many writers and one reader. Does a mpsc channel tend to produce better performance than an Arc<Mutex<VecDeque<_>>> ?

If so, what data structure is mpsc using behind the scenes ?

Since 1.67.0, the standard library's mpsc has been re-implemented with code from crossbeam-channel: Announcing Rust 1.67.0 | Rust Blog. The PR that did this merge is Merge crossbeam-channel into `std::sync::mpsc` by ibraheemdev · Pull Request #93563 · rust-lang/rust · GitHub and it has some context on why they did it.

I haven't personally benchmarked mpsc against Arc<Mutex<VecDeque<T>>>, and I don't think anyone else has, either. If you are actually interested in the difference, you will have to do your own benchmarking.

As for the implementation, it's all available here: rust/library/std/src/sync/mpmc at master · rust-lang/rust · GitHub

There is a lot to go through in there, but the high-level points of interest are:

  1. Bounded channels are backed by a fixed-size array.
  2. Unbounded channels are backed by a linked list.
  3. The internals mostly use atomic operations. According to documentation, "Channels use locks very sparingly".

The docs for the array-backed implementation links to these articles about lock-free channel design:

And the crossbeam-channel benchmark results can give you a better idea of what you're getting into.

That's basically what flume is, which you can also see in those benchmark results.

2 Likes

This topic was automatically closed 90 days after the last reply. We invite you to open a new topic if you have further questions or comments.