2017-03-05 5 views
2

Mit Clojure der Core.Async kann man einen Kanal Karte über Wandler unter Verwendung von:Core.async: Map-Kanal über Asynchron-Funktion

(def my-chan (chan (buffer 10) (map inc))) 

Aber was passiert, wenn die Mapper-Funktion selbst async ist?

sagen: Wir haben ein:

(defn async-inc [n] 
    (let [c (promise-chan)] 
    (put! (inc n)) 
    c)) 

Gibt es eine ähnliche Art und Weise präzise den Kanal über diese Funktion abzubilden? Oder würde man so etwas zu tun haben:

(def my-chan (chan (buffer 10))) 
(def my-chan2 (chan (buffer 10))) 

(go (while true 
     (>! my-chan2 
      (<! (async-inc (<! my-chan)))))) 

Es wäre nicht wirklich Mapping, da zwei Kanäle benötigt werden statt einer.

Antwort

1

Es gibt einen allgemeinen Hinweis, keinen Kanal innerhalb einer Funktion zu erstellen und ihn zurückzugeben, da er den Benutzer dieser Funktion zwingt, core.async zu verwenden. Sie können entweder eine Ausgabe über eine promise oder eine Rückruffunktion zurückgeben.

Vorausgesetzt, was Sie mit einer Ausgabe von async-inc tun möchten, ist es mit println Funktion drucken.

Return durch ein Versprechen

(defn async-inc [n] 
    (let [p (promise)] 
    (deliver p (inc n)) 
    p)) 

(println @(async-inc (<! my-chan))) 

Return durch Rückruf

(defn async-inc [n callback] 
    (callback (inc n))) 

(async-inc (<! my-chan) println) 

Aber wenn Sie keine Kontrolle über async-inc haben. Hier sind Ihre Möglichkeiten.

Verwenden <!!

(println (<!! (go (<! (async-inc (<! my-chan)))))) 

oder

Verwenden take!

(take! (go (<! (async-inc (<! my-chan)))) println) 
Verwandte Themen