Al fine di cercare di capire core.async, ho provato senza successo ad attuare la "Skynet 1 milione microbenchmark", che è:Come implementare il microbenchmark Skynet 1m con core.async?
Crea un attore (goroutine, qualunque cosa), che genera 10 nuovi attori, ognuna di esse genera altri 10 attori, ecc. fino a quando un milione di attori non sono stati creati a livello . Quindi, ognuno di essi restituisce il numero ordinale (da 0 a 999999), che vengono sommati al livello precedente e restituiti a monte, fino a raggiungere l'utente root. (La risposta dovrebbe essere 499999500000).
ci sono applicazione in molte lingue qui:
https://github.com/atemerev/skynet
Ecco il mio tentativo totalmente rotto:
(defn skynet [chan num size div]
(if (= 1 size)
(>! chan num)
(>! chan (reduce + (let [rc (async/chan)
n (/ size div)]
(doall (for [i [0 div]]
(skynet rc (+ num (* i n)) n div))
(for [i [0 div]] (<! rc))))))))
E stavo cercando di chiamare il tutto dall'interno di un blocco di andare a la REPL:
(time (go (<!! (skynet (async/chan) 0 1000000 10))))
Probabilmente sono seriamente confuso su molte cose riguardanti core.async (e anche la valutazione lazy).
Come devo risolvere questo problema e perché?
Grazie mille! Un sacco di Clojure da studiare ma questo sicuramente mi aiuterà molto, non solo la tua versione ma anche i tuoi commenti su cosa c'è di sbagliato nel mio codice. Stranamente alcuni * "a /" * sono comparsi nell'ultima riga di codice, l'ho modificato :) –
Naturalmente più lento del semplice uso di un riduttore, ma questo è il punto del benchmark. Ho provato a scrivere una versione della funzione 'skynet' che restituirebbe un canale contenente il risultato (invece di prenderne uno come argomento), e usare async/ridurre invece di una riduzione manuale e non riuscire a trovare un modo per farlo. Sarei interessato a una tale versione. Comunque, Complimenti! – nha