如何以更实用的方式从Clojure catch块中重现?

时间:2013-06-23 05:25:36

标签: clojure functional-programming

对于我正在编写的IRC机器人,我想继续尝试打开套接字,即使有UnkownHostException。我的第一个想法是这样的。

(defn open-socket [{:keys [host port] :as connection}]
  (try (java.net.Socket. host port)
    (catch java.net.UnknownHostException _ (recur connection))))

但是它不起作用,因为你不能从catch块中重现。所以我决定这样的事情:

  (let [socket (promise)
        _ (while (not (realized? socket))
            (try (deliver socket (java.net.Socket. host port))
              (catch java.net.UnknownHostException _)))
        socket @socket]
    ...

这是有效的,但这是非常必要的。有没有更多功能性的方式我可以这样做,我看不到?

2 个答案:

答案 0 :(得分:13)

只需添加or

即可
(defn open-socket [{:keys [host port] :as connection}]
  (or (try (java.net.Socket. host port)
           (catch java.net.UnknownHostException _ nil))
      (recur connection)))

答案 1 :(得分:0)

一种可能性可能是这样的吗?

(let [make-socket #(try (java.net.Socket. host port)
                     (catch java.new.UnknownHostException _))
      socket-attempts (repeatedly make-socket)
      socket (first (drop-while nil? socket-attempts))]
  socket)