在列表的每两个元素上映射一个函数
Map a function on every two elements of a list
我需要一个仅在所有其他元素上映射函数的函数,例如
(f inc '(1 2 3 4))
=> '(2 2 4 4)
我想到了:
(defn flipflop [f l]
(loop [k l, b true, r '()]
(if (empty? k)
(reverse r)
(recur (rest k)
(not b)
(conj r (if b
(f (first k))
(first k)))))))
有没有更漂亮的方法来实现这个?
最好在使用循环和递归之前查看 Clojure 的高级函数。
user=> (defn flipflop
[f coll]
(mapcat #(apply (fn ([a b] [(f a) b])
([a] [(f a)]))
%)
(partition-all 2 coll)))
#'user/flipflop
user=> (flipflop inc [1 2 3 4])
(2 2 4 4)
user=> (flipflop inc [1 2 3 4 5])
(2 2 4 4 6)
user=> (take 11 (flipflop inc (range))) ; demonstrating laziness
(1 1 3 3 5 5 7 7 9 9 11)
这个触发器不需要反转输出,它很懒,我觉得它更容易阅读。
该函数使用 partition-all
将列表分成两个项目对,并使用 mapcat 将来自调用的一系列两个元素序列连接成一个序列。
该函数使用 apply 和多个参数来处理分区集合的最后一个元素是单例(输入的长度为奇数)的情况。
(map #(% %2)
(cycle [f identity])
coll)
此外,由于您想将该函数应用于集合中的某些特定索引项目(在这种情况下甚至是索引),您可以使用 map-indexed
,如下所示:
(defn flipflop [f coll]
(map-indexed #(if (even? %1) (f %2) %2) coll))
而 是 一个 ,您可以稍微简化您的 loop
- recur
解决方案:
(defn flipflop [f l]
(loop [k l, b true, r []]
(if (empty? k)
r
(recur (rest k)
(not b)
(conj r ((if b f identity) (first k)))))))
这使用了几个常用技巧:
- 如果累积列表的顺序错误,请使用向量
相反。
- 如果可能,在条件中分解出共同元素。
我需要一个仅在所有其他元素上映射函数的函数,例如
(f inc '(1 2 3 4))
=> '(2 2 4 4)
我想到了:
(defn flipflop [f l]
(loop [k l, b true, r '()]
(if (empty? k)
(reverse r)
(recur (rest k)
(not b)
(conj r (if b
(f (first k))
(first k)))))))
有没有更漂亮的方法来实现这个?
最好在使用循环和递归之前查看 Clojure 的高级函数。
user=> (defn flipflop
[f coll]
(mapcat #(apply (fn ([a b] [(f a) b])
([a] [(f a)]))
%)
(partition-all 2 coll)))
#'user/flipflop
user=> (flipflop inc [1 2 3 4])
(2 2 4 4)
user=> (flipflop inc [1 2 3 4 5])
(2 2 4 4 6)
user=> (take 11 (flipflop inc (range))) ; demonstrating laziness
(1 1 3 3 5 5 7 7 9 9 11)
这个触发器不需要反转输出,它很懒,我觉得它更容易阅读。
该函数使用 partition-all
将列表分成两个项目对,并使用 mapcat 将来自调用的一系列两个元素序列连接成一个序列。
该函数使用 apply 和多个参数来处理分区集合的最后一个元素是单例(输入的长度为奇数)的情况。
(map #(% %2)
(cycle [f identity])
coll)
此外,由于您想将该函数应用于集合中的某些特定索引项目(在这种情况下甚至是索引),您可以使用 map-indexed
,如下所示:
(defn flipflop [f coll]
(map-indexed #(if (even? %1) (f %2) %2) coll))
而 loop
- recur
解决方案:
(defn flipflop [f l]
(loop [k l, b true, r []]
(if (empty? k)
r
(recur (rest k)
(not b)
(conj r ((if b f identity) (first k)))))))
这使用了几个常用技巧:
- 如果累积列表的顺序错误,请使用向量 相反。
- 如果可能,在条件中分解出共同元素。