Clojure:Clojure中的llegalArgumentException重复 - 类型不匹配

时间:2014-10-05 00:58:17

标签: clojure

以下是用于与byte一起使用的循环/重复结构的简化示例。

(defn test-lr []
  (loop [last-byte (byte 0)
         bytez (map byte '(1 2 3 4))
         answer '()]
    (if (empty? bytez)
      answer
      (recur (first bytez)
             (rest bytez)
             (cons (bit-or (first bytez last-byte) answer))))))

每当我尝试在REPL中编译此代码时,都会收到以下错误。

CompilerException java.lang.IllegalArgumentException: 
recur arg for primitive local: last_byte is not matching primitive,
had: Object, needed: byte, compiling:...

该错误表明,loop绑定期望的内容与recur对第一个参数的调用之间的类型不匹配。他们似乎都是byte,所以我不知道问题是什么。

user=> (type (byte 0))
java.lang.Byte
user=> (type (first (map byte '(1 2 3))))
java.lang.Byte

1 个答案:

答案 0 :(得分:2)

我在Clojure IRC频道上询问了这个问题,用户合作和dbasch帮助了我。我对该对话的理解如下。

似乎问题是last-byte绑定中loop的绑定是Java原语byte,而(first bytez)实际上返回java.lang.Byte ,源自java.lang.Object。因此,在byte的调用中传递的预期java.lang.Byte Java原语与Object(从recur派生)之间存在类型不匹配:因此错误信息。

解决方法是将recur参数转换为基元:(byte (first bytez))

另一种选择是使用byte-array并使用aget进行访问。

一般来说,了解您正在使用的类型非常重要,请记住原语和盒装类型不一定是可以互换的。似乎Clojure函数通常(永远不会)返回Java原语。