Clojure:"线程优先"宏 - >和"线程最后"宏 - >>

Pau*_*uli 1 clojure

我正在4clojure.com 处理问题#74,我的解决方案如下:

(defn FPS [s]
  (->>
    (map read-string (re-seq #"[0-9]+" s))
    (filter #(= (Math/sqrt %) (Math/floor (Math/sqrt %))))
    (interpose ",")
    (apply str)))
Run Code Online (Sandbox Code Playgroud)

它工作得很好.但如果我使用"线程优先"宏 - >

(defn FPS [s]
  (->
    (map read-string (re-seq #"[0-9]+" s))
    (filter #(= (Math/sqrt %) (Math/floor (Math/sqrt %))))
    (interpose ",")
    (apply str)))
Run Code Online (Sandbox Code Playgroud)

它返回: ClassCastException clojure.lang.LazySeq cannot be cast to clojure.lang.IFn clojure.core/apply (core.clj:617)

为什么在这个问题上" - >"不能被" - >"取代?

Tom*_*omo 8

Thread-last宏(->>)将每个插入作为下一个表单的最后一个元素.Thread-first宏(->)将其作为第二个元素插入.

所以这:

(->> a
     (b 1)
     (c 2))
Run Code Online (Sandbox Code Playgroud)

转换为:(c 2 (b 1 a)),而

(-> a
    (b 1)
    (c 2))
Run Code Online (Sandbox Code Playgroud)

转换为:(c (b a 1) 2).


Chi*_*ron 8

在Clojure REPL中:

user=> (doc ->)
-------------------------
clojure.core/->  
([x & forms])
Macro   
 Threads the expr through the forms. Inserts x as the
 second item in the first form, making a list of it if it is not a
 list already. If there are more forms, inserts the first form as the


 user=> (doc ->>)
 -------------------------
 clojure.core/->>
 ([x & forms])
  Macro   
  Threads the expr through the forms. Inserts x as the
  last item in the first form, making a list of it if it is not a
  list already. If there are more forms, inserts the first form as the
  last item in second form, etc.
Run Code Online (Sandbox Code Playgroud)

filterfunction期望第一个参数是一个函数,而不是一个序列,并且通过使用S ->,你不满足它的要求.

这就是clojure.lang.LazySeq cannot be cast to clojure.lang.IFn你的代码中出现异常的原因.