代码之家  ›  专栏  ›  技术社区  ›  Timothy Baldridge

阻塞通道与异步消息传递

  •  8
  • Timothy Baldridge  · 技术社区  · 14 年前

    我注意到了两种“传递消息”的方法。一个是我见过的Erlang,另一个是Stacklesspython。据我所知,这就是区别

    Erlang样式-消息被发送并排队到接收进程的邮箱中。从那里,它们在先进先出的基础上被删除。一旦第一个进程发送消息,它就可以自由地继续。

    python-style-处理发送到进程b的队列。b当前正在执行一些其他操作,因此a将被冻结,直到b准备好接收。一旦B打开一个读取通道,A发送数据,然后它们都继续。

    现在我看到Erlang方法的优点是您没有任何阻塞的进程。如果B无法接收,A仍可以继续。然而,我在我编写的一些程序中注意到,由于消息的流入大于流出,Erlang消息框可能会充满数百(或数千)条消息。

    现在我还没有用任何一种框架/语言编写过一个大型程序,所以我想知道你的经验是这样的,如果这是我应该担心的事情的话。

    是的,我知道这是抽象的,但我也在寻找相当抽象的答案。

    2 回复  |  直到 11 年前
        1
  •  6
  •   Christian    14 年前

    我在Erlang编程方面的经验是,当您期望较高的消息传递率(即,生产者比消费者更快)时,您可以添加自己的流控制。一个简单的场景

    • 消费者将:发送消息,等待确认,然后重复。
    • 生产者将:等待消息,在消息接收和处理时发送ACK,然后重复。

    你也可以将其颠倒,生产者等待消费者来获取下一条可用的消息。

    这些方法和其他流量控制可以隐藏在函数后面,第一个方法在 gen_server:call/2,3 反对 gen_server OTP行为过程。

    我认为异步消息传递在Erlang中是更好的方法,因为当延迟很高时,您可能非常希望在计算机之间消息传递时避免同步。然后,我们可以用巧妙的方法来实现流控制。比如说,要求消费者对生产商发送的每N条消息进行确认,或者时不时地发送一条特殊的“当您收到这条消息时给我打电话”消息来计算ping时间。

        2
  •  3
  •   Rhamphoryncus    14 年前

    一般来说,这是无边界队列与有边界队列。无堆叠通道可以视为0大小队列的特殊情况。

    有界队列有死锁的倾向。两个线程/进程试图互相发送消息,都有一个完整的队列。

    无边界队列有更细微的失败。正如您提到的,大型邮箱无法满足延迟要求。足够远,它最终会溢出;没有无限内存这样的东西,所以它实际上只是一个有界队列,有一个巨大的限制,当进程满时会中止进程。

    哪一个最好?很难说。这里没有简单的答案。

    推荐文章