For example we want the function f that does this:-

(f '(1 2 3 4 5 6) 2) => ((1 3 5) (2 4 6)) ; split into two

(f '(1 2 3 4 5 6) 3) => ((1 4) (2 5) (3 6)) ; split into three

OK, so I expect I will want code to get every nth element from a sequence - every 2nd, every 3rd one etc. The built-in function

**partition-all**splits a sequence into sequences of a nominated length: so all I want from this is the first element of every sub-sequence. I map

**first**onto the sequence of sequences returned by partition-all:-

user=> (def t '(1 2 3 4 5 6))

#'user/t

user=> t

(1 2 3 4 5 6)

user=> (partition-all 2 t)

((1 2) (3 4) (5 6))

user=> (partition-all 3 t)

((1 2 3) (4 5 6))

user=> (map first (partition-all 2 t))

(1 3 5)

user=> (map first (partition-all 3 t))

(1 4)

Then moving on I will want to get every nth element but not starting at the beginning, starting at some i-th element in. So I have to

**drop**some elements before the rest of the function gets it - something like this:-

defn every-nth-from-i

"return every nth item from sequence s starting from element i (counting from zero)"

[n s i]

(map first (partition-all n (drop i s))))

user=> (every-nth-from-i 3 t 0)

(1 4)

user=> (every-nth-from-i 3 t 1)

(2 5)

user=> (every-nth-from-i 3 t 2)

(3 6)

Now the result I want is a sequence of all the sequences generated by this code, for each value of i up to the length of the sub-sequences I want to generate. Well, one less. That's ok, given n I want to

**map**the numbers in

**(range n)**to the every-nth code.

(def reverse-interleave

(fn [n s]

(map

(fn [i] (map first (partition-all n (drop i s))))

(range 0 n))))

I don't need to explicitly pass n and s to the internal function because it executes in the environment where they are already available.

Does this work?

user=> (reverse-interleave 2 t)

((1 3 5) (2 4 6))

user=> (reverse-interleave 3 t)

((1 4) (2 5) (3 6))

Actually that turned out simpler than I expected.

## No comments:

## Post a Comment