Clojure – why do I hang when a block is inserted into a channel? (core.async)

Consider the following code snippet:

(let [chs (repeatedly 10 chan)]
  (doseq [c chs]
    (>!! c "hello"))
  (doseq [c chs]
    (println (<!! c))))

Performing this operation will permanently suspend Why?

If I do (go (>! C "hello"), it works well

Solution

For asynchronous placement, use clojure core. async / put!

(let [chs (repeatedly 10 chan)]
  (doseq [c chs]
    (put! c "hello"))
  (doseq [c chs]
    (println (<!! c))))

This example is blocking is a synchronization constraint between different processes > >!! And Clojurescript has only one thread Therefore, its core The async implementation does not even contain >! / < If you write code that is intended to be compatible with clojurescript, you can only take it from the channel in go routes or from the derived values passed to higher-level functions! And always put it in go routine or use put! Is (go (>! Ch V)) equivalent to (put! Ch V)?

Yes, but not the same Let go! Is an API wrapper around channel async. impl. Protocols / writeport placement channel implementation! method. The macro extension of (go (>! Ch V)) eventually occurs in the same method call, but it is wrapped in many generated state machine code so that it is possible to stop the placement operation and pause the execution of the Go program until the consumer is ready to start from CH (try (macro expansion ` (go (>! Ch V))) himself) It is a waste to generate a deblocking and only do an asynchronous placement operation, which is worse than calling put! right off. To generate and return an additional channel, you can put it to the body's results This allows you to wait for execution to complete without having to execute in the example (for asynchronous operations)

The content of this article comes from the network collection of netizens. It is used as a learning reference. The copyright belongs to the original author.
THE END
分享
二维码
< <上一篇
下一篇>>