为什么 lein 运行 挂了?

Why does lein run hang?

我已经为 here 中的练习 2 创建了 Leiningen 项目。我的代码如下所示:

(ns random-quotes.core
  (:require [clojure.string :as str])
  (:gen-class))

(defn word-count [s]
  (frequencies (str/split (first (str/split s #"\n")) #"\s")))

(def quote-url "http://www.braveclojure.com/random-quote")

(def total-word-count (atom {}))

(defn update-word-count []
  (future
    (swap! total-word-count
           (partial merge-with +)
           (word-count (slurp quote-url)))))

(defn quote-word-count [n]
  (doseq [quote-future (doall (repeatedly n update-word-count))]
    @quote-future)
  @total-word-count)

(defn -main [n]
  (doseq [entry (sort-by val (quote-word-count (bigdec n)))]
    (println entry)))

一切都非常简单。当我 运行,例如 lein repl 中的 (-main 5),它 运行s,打印,并且 returns 如预期的那样。但是,当我尝试 lein run 5 时,它会 运行s 并打印但永远不会退出,所以我不得不使用 Ctrl+C 拿回我的终端机。

知道为什么会这样吗?

Clojure 有一个线程池,它保留 运行 供代理使用。因为那些线程仍然存在,所以 JVM 无法判断您的程序已完成。它只是坐在那里等待特工退出。您可以按照 here 所述在程序末尾调用 (shutdown-agents) 来完成它们。期货使用代理。

clojure.core/future-call 这样调用代理:

(let [f (binding-conveyor-fn f)
      fut (.submit clojure.lang.Agent/soloExecutor ^Callable f)]

这实际上启动了您的代码 运行。您不会是唯一表达 some criticism 的人,我们都希望找到更优雅的解决方案。