在Clojure中将'map'与不同大小的集合一起使用 [英] Using 'map' with different sized collections in clojure
问题描述
我想了解在Clojure中处理不同大小的集合的惯用方式.有什么办法可以让函数'map'用默认值填充集合的其余部分?
作为一个例子,假设我有3个向量:
(def x [1 2 3 4])
(def y [1 2 3 4 5])
(def z [1 2 3 4 5 6 7])
(map + x y z) ; yields (3 6 9 12)
在这种情况下,我如何用零填充x和y并产生这样的收益:
(3 6 9 12 10 6 7)
map
本身并不做,但是您可以结合使用concat
和repeat
来获得所需的结果:
(def x [1 2 3 4])
(def y [1 2 3 4 5])
(def z [1 2 3 4 5 6 7])
(map +
(concat x (repeat 0))
(concat y (repeat 0))
z) ; => (3 6 9 12 10 6 7)
这是一个草图,您可以将其抽象一些,因此您无需知道哪个集合最长. (在上面的代码段中,如果将concat
的所有集合concat
concat
,则将有一个无限的序列).
(defn map-longest
[f default & colls]
(lazy-seq
(when (some seq colls)
(cons
(apply f (map #(if (seq %) (first %) default) colls))
(apply map-longest f default (map rest colls))))))
(map-longest +
0
[1 2 3 4]
[1 2 3 4 5]
[1 2 3 4 5 6 7]) ; => (3 6 9 12 10 6 7)
您可以看到其他几种方法来作为之前有关堆栈溢出的问题的答案.
>I'd like to understand the idiomatic way with which to operate over collections of different sizes in clojure. Is there a way I can tell the function 'map' to pad the rest of a collection with some default value?
As an example, suppose I have 3 vectors:
(def x [1 2 3 4])
(def y [1 2 3 4 5])
(def z [1 2 3 4 5 6 7])
(map + x y z) ; yields (3 6 9 12)
In this case, how can I pad x and y with zeroes and have this yield:
(3 6 9 12 10 6 7)
map
doesn't do it itself, but you can use a combination of concat
and repeat
to obtain the desired result:
(def x [1 2 3 4])
(def y [1 2 3 4 5])
(def z [1 2 3 4 5 6 7])
(map +
(concat x (repeat 0))
(concat y (repeat 0))
z) ; => (3 6 9 12 10 6 7)
Here's the API documentation for concat, and for repeat.
And here's a sketch of how you could abstract this away a bit, so you don't need to know which of the collections is longest. (In the snippet above, if you concat
all the collections to (repeat 0)
you'll have an infinite sequence).
(defn map-longest
[f default & colls]
(lazy-seq
(when (some seq colls)
(cons
(apply f (map #(if (seq %) (first %) default) colls))
(apply map-longest f default (map rest colls))))))
(map-longest +
0
[1 2 3 4]
[1 2 3 4 5]
[1 2 3 4 5 6 7]) ; => (3 6 9 12 10 6 7)
You can see a couple other approaches as answers to this previous question on Stack Overflow.
这篇关于在Clojure中将'map'与不同大小的集合一起使用的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!