有界与无界通道

至今为止,我们一直在使用无界通道。你可以发送任意数量的消息,通道会根据需要扩容以容纳它们。但在多生产者单消费者场景下,这可能带来问题:如果生产者入队消息的速度超过消费者处理速度,通道将会不断增长,有可能消耗掉所有可用内存。

我们的建议是绝不在生产系统中使用无界通道。你应该总是通过有界通道对可入队消息的数量设置一个上限。

有界通道

有界通道具有固定的容量。你可以通过调用sync_channel并传入大于零的容量来创建一个有界通道:

#![allow(unused)]
fn main() {
use std::sync::mpsc::sync_channel;

let (sender, receiver) = sync_channel(10);
}

receiver的类型与之前相同,为Receiver<T>。而sender则是一个SyncSender<T>的实例。

发送消息

通过SyncSender发送消息有两种不同的方法:

  • send:如果通道中有空间,它会将消息入队并返回Ok(())。如果通道已满,它会阻塞等待直到有空间可用。
  • try_send:如果通道中有空间,它会将消息入队并返回Ok(())。如果通道已满,它会返回Err(TrySendError::Full(value)),其中value是未能发送的消息。

根据你的应用场景,你可能选择使用其中之一。

反压

使用有界通道的主要优势在于它们提供了一种反压机制。它们迫使生产者在消费者无法跟上时减速。这种反压可以进一步传播至整个系统,可能影响整体架构并防止终端用户以过多请求压垮系统。