简体   繁体   English

Clojure ClassCastException长到IFn

[英]Clojure ClassCastException long to IFn

I'm new to clojure and I am trying to make a small program that does math with complex numbers. 我是clojure的新手,我正在尝试制作一个用复数做数学的小程序。 I've tried multiple versions of the multiply function and they all give the same error. 我尝试了多个版本的乘法函数,它们都给出了相同的错误。 For some other functions, using let fixed it but not here. 对于其他一些功能,使用let修复它但不在这里。 im-make just returns a vector with the real and imaginary numbers. im-make只返回带有实数和虚数的向量。

(defn im-mult
  ([i j]
    (let [a (first i)
          b (second i)
          x (first j)
          y (second j)]
  (im-make (- (* (a) (b)) (* (x) (y)))
             (+ (* (a) (b)) (* (x) (y)))))))

given two vectors with a real and imaginary number, => (im-mult xy) 给出两个具有实数和虚数的向量,=>(im-mult xy)

ClassCastException java.lang.Long cannot be cast to clojure.lang.IFn ComplexMath.core/im-mult (NO_SOURCE_FILE:7) ClassCastException java.lang.Long无法强制转换为clojure.lang.IFn ComplexMath.core / im-mult(NO_SOURCE_FILE:7)

I just want to say, wow! 我只是想说,哇! Didn't think clojure had this much backing around here, thanks for the suggestions, the error was of course parenthesis and incorrect multiplying. 没想到clojure在这里有这么多的支持,感谢你的建议,错误当然是括号和不正确的乘法。

1) you need to get rid of the extra parens around a, b, x, and y. 1)你需要摆脱a,b,x和y周围的额外parens。

2) anytime you see a bunch of first and second, that's a good clue that you should be destructuring your inputs instead: 2)任何时候你看到一堆第一和第二,这是一个很好的线索,你应该解构你的输入:

(defn im-mult
  [i j]
  (let [[a b] i
        [x y] j]
    (im-make (- (* a b) (* x y))
             (+ (* a b) (* x y)))))

I would always recommend this over #1. 我会一直推荐#1。 This might be a good place to stop for readability, but for grins we can keep pushing it... 这可能是一个停止可读性的好地方,但对于笑容我们可以继续推动它......

3) I observe that (* ab) and (* xy) are used twice, so there is really no need to destructure at all - we can just apply * to i and j: 3)我观察到(* ab)和(* xy)被使用了两次,所以根本不需要进行结构化 - 我们可以将*应用于i和j:

(defn im-mult
  [i j]
  (let [ab (apply * i)
        xy (apply * j)]
    (im-make (- ab xy)
             (+ ab xy))))

4) I observe that you're applying the same operation to both inputs, so might as well map the operation across the inputs. 4)我观察到你正在对两个输入应用相同的操作,因此也可以在输入上映射操作。

(defn im-mult
  [i j]
  (let [m (map #(apply * %) [i j])]
    (im-make (apply - m)
             (apply + m))))

5) Same observation for - and +... 5)相同的观察 - 和+ ...

(defn im-mult
  [i j]
  (let [m (map #(apply * %) [i j])
        s (map #(apply % m) [- +])]
    (apply im-make s)))

At this point, it's admittedly harder to see the intent of the code. 在这一点上,很难看到代码的意图。 However, I think one reason is that you've fixed the number of inputs to 2. My suspicion is that there is an n-dimensional algorithm here and taking [& i] as inputs would lead you to a more beautiful place while also improving the code. 但是,我认为一个原因是你已经将输入数量固定为2.我怀疑这里有一个n维算法,以[&i]为输入会带你到一个更美丽的地方,同时也在改善编码。

Those extra parentheses aroung a , b , x and y are not needed. 不需要那些额外的括号abxy Besides, they make Clojure try to interpret numbers as functions. 此外,他们让Clojure尝试将数字解释为函数。 This should fix it: 这应该解决它:

(defn im-mult
  ([i j]
    (let [a (first i)
          b (second i)
          x (first j)
          y (second j)]
      (im-make (- (* a b) (* x y))
           (+ (* a b) (* x y))))))

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM