Clojure 将单个变量传递给函数

Clojure Passing Individual Variables to Function

我正在尝试将一些包含节点列表的向量传递给 clojure 中的函数,如果我要输入变量,该函数就可以工作,但我不确定如何从每个向量中传递单个变量一次。

(def ItemPickUp [:a1 :Mail])
(def ItemDestinations [:Storage :a1])
(def Robot {[ItemPickUp] [ItemDestinations]})



(defn shortestPath [g start dest]
(let [not-destination? (fn [[vertex _]] (not= vertex dest))]
(-> (shortest-paths g start)
    (->> (drop-while not-destination?))
    first
    (nth 2))))

(apply shortestPath G (apply first Robot)((apply second Robot)))

我需要使用机器人将一个变量从 ItemPickUp 和 ItemDestination 传递到 shortestPath 中,但不是传递其中的一个变量,而是同时传递 :a1 和 :Mail,另一个则相反。

如何单独传递每个变量,以便第一次迭代的前两个变量是 :a1 和 :Storage 等等?

谢谢。

在 Clojure 中,这通常使用 map - it takes a function f and any number of collections and lazily produces a sequence of (f (first coll1) (first coll2)...), (f (second coll1) (second coll2)...)...
所以它应该只是

(map (partial shortestPath G) ItemPickup ItemDestinations)

(一些其他功能语言区分单集合 mapping 和多集合 zipping - 我相信 Haskell 在这里有影响。它需要这个,因为它的功能已经固定arities,所以你有 zipWithzipWith3 等。用括号表示参数的数量意味着 Lisps 不必处理它。)

如果 (def Robot [[ItemPickUp] [ItemDestinations]]) 并且您想使用它,您可以这样做:

(apply map (partial shortestPath G) Robot)

在这种情况下应用将减少到:

(map (partial shortestPath G) (first Robot) (second Robot))

如果 Robot 有两个元素以外的元素,当然会抛出 ArityException。

您可以将 apply 视为将括号(函数调用)移动到他的第一个参数并从最后一个参数(如果有的话)中取出括号。