我该如何迭代序列?

dj3*_*dj3 3 clojure

下面是我尝试迭代一系列地图; 由于转换错误导致代码失败:Exception in thread "main" java.lang.RuntimeException: java.lang.ClassCastException: clojure.lang.Cons cannot be cast to java.util.Map$Entry.

任何人都可以解释/演示我应该如何迭代结果集?谢谢.

(with-connection db
                 (with-query-results rs ["select category from users group by category"]
                                     (doall
                                       (for [s [rs]] 
                                       (do (println (val s)))))))
Run Code Online (Sandbox Code Playgroud)

kot*_*rak 5

你把它包裹rs成一个矢量.因此s将绑定到整个序列,而不是单个映射条目.所以当你打电话时val它不知道如何处理序列.因此例外.这应该工作:

(with-connection db
  (with-query-results rs ["select category from users group by category"]
    (doall
      (for [rec rs
            s   rec] 
        (do
          (println (val s)))))))
Run Code Online (Sandbox Code Playgroud)

然而,丑陋doalldo周围for应该响铃,有些东西可以改善.确实for用于构建另一个懒惰序列.对于您的示例中的打算,这不适用于副作用.你应该doseq 在这种情况下使用.

(with-connection db
  (with-query-results rs ["select category from users group by category"]
    (doseq [rec rs
            s   rec]
      (println (val s)))))
Run Code Online (Sandbox Code Playgroud)

绑定的接口doseqfor.的接口相同.然而,它立即执行,因此立即实现任何副作用.如果你在for的主体中放置多个表达式,你必须将它包装成一个do.这提醒人们身体应该产生价值.然而,多个表达指示副作用.doseq因此,do为你包裹身体.所以你可以轻松拥有多个表达式.例如:

(doall
  (for [s seq-of-maps]
    (do
      (println (key s))
      (println (val s)))))

(doseq [s seq-of-maps]
  (println (key s))
  (println (val s)))))
Run Code Online (Sandbox Code Playgroud)

根据经验:你需要副作用吗?寻找开始的东西do!

根据经验2:如果看起来很丑陋(参见上面的比较),这应该响铃.