4clojure第43个问题逆向交错(Reverse Interleave)

来源:互联网 发布:手机淘宝试用中心在哪 编辑:程序博客网 时间:2024/06/06 01:10
Reverse Interleave
 

Difficulty:MediumTopics:seqs
Write a function which reverses the interleave process into x number of subsequences.
test not run
(= (__ [1 2 3 4 5 6] 2) '((1 3 5) (2 4 6)))
test not run
(= (__ (range 9) 3) '((0 3 6) (1 4 7) (2 5 8)))
test not run
(= (__ (range 10) 5) '((0 5) (1 6) (2 7) (3 8) (4 9)))


解决方案:如果简单的满足以上条件,即序列的大小刚好是间隔位置的倍数,则答案可以很简单
(fn [v n]   (apply map list (partition n v)))
但是如果序列的大小和间隔位置数不是倍数关系,则需要填充nil到原来的序列中,使得满足倍数的关系,然后再map应用函数的过程中剔除nil。
(ns for-clojure.problem43)(defn partition-seq-with-n-element   [v n]  (apply map (fn [& x] (remove nil? x))   (let [cnt (count v)         size (int (Math/ceil (/ cnt n)))]      (partition n                (concat v (repeat (- (* n size) cnt) nil))))))(partition-seq-with-n-element [1 2 3 4 5 6 7] 2)

这里一个为什么使用了remove 而不是drop-while因为drop-while只是drop那先返回nil的元素,而(nil? nil)为true,所以不会被删除。
remove删除的是返回true的元素,而返回nil的元素是不会被删除的,所以这里正好要使用remove。

partition-all与partition的区别 partition把序列分成等大的片段,多余的会被舍弃,而partition-all会把多余的元素保留。
原创粉丝点击