有没有办法在并行执行时采用一组期货并将它们作为一个组来阻止?
Is there a way to take a set of futures and block on them as a group while they execute in parallel?
我希望能够等待一组函数。我希望它们并行执行,但会阻塞直到最后一个 future 完成。 (我不希望它们按顺序执行,例如 (do @(future-1) @(future-2))
)
类似
(declare long-running-fn-1)
(declare long-running-fn-2)
(let [results (wait-for-all
(long-running-fn-1 ...)
(long-running-fn-2 ...)]
(println "result 1" (first results)
(println "result 2" (second results))
Future 在定义时被添加到用于 send
的同一个线程池中。只要该池中有足够的空闲线程(其大小将略大于可用的 CPU 内核数),计算就会立即开始。
(doall @(future ...) @(future ...))
的问题是第二个 future
直到 在 第一个被取消引用后才创建。
这里是你的代码的一个稍微修改过的版本,它定义了 both 个期货(开始计算),然后再取消对它们中的任何一个的引用;你会看到它只需要 5 秒而不是 10 秒:
(time
(let [future-1 (future (Thread/sleep 5000))
future-2 (future (Thread/sleep 5000))]
[@future-1 @future-2]))
这里还有一个例子,说明了并行执行+同步取消引用:
(letfn [(mk-fut [sleep-ms res]
(future
(Thread/sleep sleep-ms)
(println "return" res "after" sleep-ms "ms")
res))]
(let [futures (mapv mk-fut
(repeatedly #(rand-int 2000))
(range 10))]
(mapv deref futures)))
;; return 3 after 104 ms
;; return 8 after 278 ms
;; return 0 after 675 ms
;; return 6 after 899 ms
;; return 1 after 928 ms
;; return 2 after 1329 ms
;; return 9 after 1383 ms
;; return 4 after 1633 ms
;; return 5 after 1931 ms
;; return 7 after 1972 ms
;;=> [0 1 2 3 4 5 6 7 8 9]
(输出打印的顺序在调用之间会有所不同,而生成的向量是相同的)您可以看到所有期货 运行 是并行的,同时按特定顺序生成和取消引用。
使用pcalls
或pvalues
:
test1.core=> (pcalls #(inc 1) #(dec 5))
(2 4)
test1.core=> (pvalues (inc 1) (dec 5))
(2 4)
他们在内部使用 pmap
并行执行函数,并在处理所有函数时使用 return 惰性结果序列。
我希望能够等待一组函数。我希望它们并行执行,但会阻塞直到最后一个 future 完成。 (我不希望它们按顺序执行,例如 (do @(future-1) @(future-2))
)
类似
(declare long-running-fn-1)
(declare long-running-fn-2)
(let [results (wait-for-all
(long-running-fn-1 ...)
(long-running-fn-2 ...)]
(println "result 1" (first results)
(println "result 2" (second results))
Future 在定义时被添加到用于 send
的同一个线程池中。只要该池中有足够的空闲线程(其大小将略大于可用的 CPU 内核数),计算就会立即开始。
(doall @(future ...) @(future ...))
的问题是第二个 future
直到 在 第一个被取消引用后才创建。
这里是你的代码的一个稍微修改过的版本,它定义了 both 个期货(开始计算),然后再取消对它们中的任何一个的引用;你会看到它只需要 5 秒而不是 10 秒:
(time
(let [future-1 (future (Thread/sleep 5000))
future-2 (future (Thread/sleep 5000))]
[@future-1 @future-2]))
这里还有一个例子,说明了并行执行+同步取消引用:
(letfn [(mk-fut [sleep-ms res]
(future
(Thread/sleep sleep-ms)
(println "return" res "after" sleep-ms "ms")
res))]
(let [futures (mapv mk-fut
(repeatedly #(rand-int 2000))
(range 10))]
(mapv deref futures)))
;; return 3 after 104 ms
;; return 8 after 278 ms
;; return 0 after 675 ms
;; return 6 after 899 ms
;; return 1 after 928 ms
;; return 2 after 1329 ms
;; return 9 after 1383 ms
;; return 4 after 1633 ms
;; return 5 after 1931 ms
;; return 7 after 1972 ms
;;=> [0 1 2 3 4 5 6 7 8 9]
(输出打印的顺序在调用之间会有所不同,而生成的向量是相同的)您可以看到所有期货 运行 是并行的,同时按特定顺序生成和取消引用。
使用pcalls
或pvalues
:
test1.core=> (pcalls #(inc 1) #(dec 5))
(2 4)
test1.core=> (pvalues (inc 1) (dec 5))
(2 4)
他们在内部使用 pmap
并行执行函数,并在处理所有函数时使用 return 惰性结果序列。