簡體   English   中英

在clojure中有一個“:until”之類的命令嗎?

[英]Is there a “:until” like command in clojure?

我想執行以下嵌套操作,直到滿足期限為止。是否有:until關鍵字在條件匹配時停止進行進一步操作。

這個命令生成了Pythagoran Triplet 3 4 5.一旦它到達那個數字序列,我不希望它做任何其他事情。

(for [a (range 1 100)
      b (range 1 100)
      c (list (Math/sqrt (+ (Math/pow (int a) 2) (Math/pow (int b) 2))))
      :when (= 12 (+ a b c))]
     (list a b c))

:while處於短路試驗for表達式。 列表元素將在第一次遇到失敗的測試時生成。

在你的情況下

(for [<code omitted> :while (not (= 12 (+ a b c)))] (list a b c))

一旦發現三元組總和為12,就會停止生成元素。

但是有一個問題,它不能滿足你的期望。 由於測試失敗 ,三聯體本身不會成為結果的一部分。

如果您只查找單個匹配結果,則列表推導可能不是最佳解決方案。 為什么不使用循環?

(loop [xs (for [a (range 1 100)
                b (range 1 100)] [a, b])]
  (when (seq xs)
    (let [[a, b] (first xs)
          c (Math/sqrt (+ (Math/pow (int a) 2)
                          (Math/pow (int b) 2)))]
      (if (not (= 12 (+ a b c)))
        (recur (next xs))
        (list a b c)))))

由於收益率序列,你會選擇第一要素獲得所需的結果:

(first (for [a (range 1 100)
             b (range 1 100)
             c (list (Math/sqrt (+ (Math/pow (int a) 2) 
                                   (Math/pow (int b) 2))))
             :when (= 12 (+ a b c))]
          (list a b c))

由於懶惰,僅計算生成列表的第一個元素,這可以通過副作用來證明:

user=> (first
        (for [a (range 1 100)
              b (range 1 100)
              c (list (Math/sqrt (+ (Math/pow (int a) 2) 
                                    (Math/pow (int b) 2))))
              :when (= 12 (+ a b c))]
          (do (println "working...")
              (list a b c))))
working...
(3 4 5.0)

(for ...)附帶一個:let修飾符,因此不需要在列表中包裝c:

(for [a (range 1 100)
      b (range 1 100)
      :let [c (Math/sqrt (+ (Math/pow (int a) 2) 
                            (Math/pow (int b) 2)))]
      :when (= 12 (+ a b c))]
  (list a b c))

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM