首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Core.async <!信道死锁

Core.async <!信道死锁
EN

Stack Overflow用户
提问于 2015-11-20 16:55:07
回答 1查看 334关注 0票数 2

为什么阿尔法会提前停下来,而我希望它表现得像贝塔?阿尔法和贝塔之间唯一的区别是>!put!,如下所示。

阿尔法:

代码语言:javascript
复制
user=> (def q (chan))
#'user/q
user=> (def counter (atom 0))
#'user/counter
user=> (defn mg [event-queue]
  #_=>      (go-loop [event (<! event-queue)]
  #_=>       (swap! counter inc)
  #_=>       (when (< @counter 4)
  #_=>         (println "counter: " @counter)
  #_=>         (>! event-queue {:a @counter})      ;; Here's the only difference
  #_=>         (println "event: " event)
  #_=>         (recur (<! event-queue)))))
#'user/mg
user=> (mg q)
#object[clojure.core.async.impl.channels.ManyToManyChannel 0x3a1ffd56 "clojure.core.async.impl.channels.ManyToManyChannel@3a1ffd56"]
user=> (put! q "hi")
counter:  true
1
user=>

测试版:

代码语言:javascript
复制
user=> (def q (chan))
#'user/q
user=> (def counter (atom 0))
#'user/counter
user=> (defn mg [event-queue]
  #_=>   (go-loop [event (<! event-queue)]
  #_=>    (swap! counter inc)
  #_=>    (when (< @counter 4)
  #_=>      (println "counter: " @counter)
  #_=>      (put! event-queue {:a @counter})      ;; Here's the only difference
  #_=>      (println "event: " event)
  #_=>      (recur (<! event-queue)))))
#'user/mg
user=> (mg q)
#object[clojure.core.async.impl.channels.ManyToManyChannel 0x72c9b65a "clojure.core.async.impl.channels.ManyToManyChannel@72c9b65a"]
user=> (put! q "hi")
true
counter:  1
event:  hi
counter:  2
event:  {:a 1}
counter:  3
event:  {:a 2}
user=> 

同样有趣的是,在执行Alpha之后,通道#'user/q被正确地排队:

代码语言:javascript
复制
user=> (take! q println)
event:  hi
{:a 1}
nil
user=> 

同样的结果出现在Clojure和Clojurescript中。这是某种类型的死锁,还是应该发生的?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2015-11-20 17:20:22

这是意料之中的。

通道q是在没有缓冲区的情况下创建的,所以当一个值与>!放在一起时,它将阻塞(停放) go-loop,直到另一个线程准备使用<!来使用该值为止。

解决这一问题的一种方法是给q一个带有(def q (chan 1))的1槽缓冲区。缓冲区允许将1值放置在通道中,而不阻塞发送方。

由于put!是异步wrt,所以Beta的行为有所不同。调用者--它使用一个单独的线程将新值放置在通道中。这样可以避免阻塞当前的go-loop,从而允许读取通道并继续进行。

票数 5
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/33832040

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档