有时候我很难在Clojure中包装函数或宏。
例如,Clojure Mongo提供了一个DSL来查询集合:with-collection,这是一个宏。
使用它的一种方法如下所示:
(with-collection db coll
(find {})
(sort (array-map :score -1 :name 1)))
我想创建一个接收排序函数的函数,并使用-collection调用。
(defn find [sort]
(with-collection my-db my-coll
(find {})
sort
)
如果我尝试调用该函数,我会收到以下错误:ClassCastException clojure.lang.PersistentList无法强制转换为clojure.lang.IFn
(find (sort (array-map :score -1 :name 1))
我想这是因为正在评估排序,并且with-collection需要一个函数。
如果我尝试引用,我会收到以下错误:ClassCastException clojure.lang.PersistentList无法强制转换为clojure.lang.IFn
(find (quote sort (array-map :score -1 :name 1)))
如果我尝试传递一个匿名函数,我会收到以下错误:ArityException传递给args(1)的错误数量为:main / eval139628 / fn - 139629
(find #(sort (array-map :score -1 :name 1))
是否可以使用函数包装这种宏?感谢。
答案 0 :(得分:3)
事情是with-collection
宏扩展为->
,因此您的函数应该将coll作为第一个参数。你也可以使用`find函数来遮蔽monger find
函数。可能你应该做这样的事情:
(defn my-find [sort]
(with-collection my-db my-coll
(find {})
sort)
并将其称为:
(my-find #(sort % (array-map :score -1 :name 1))