# Any way to reverse span and join two span in Mathematica?

I port a matlab code to mathematica. In the original matlab code, I use ":" to pick up the desired elements in a matrix. In mathematica, I find in the documentation that the span operator is ";;" (without quotation). I have a big nx1 matrix (n is odd), the kth element is the very middle element of the matrix, I am going to pick up all element from k with interval 2, I am currently use the following code

M[[k;;1;;-2]]  (* M is the matrix of nx1*)
M[[k+2;;n;;2]] (* M is the matrix of nx1*)


It does return the desired elements; however, I want to maintain one index instead. Is that any way to combine the index such that

idx = REVERSE(k;;1;;-2) JOIN k+2;;n;;2


Also, REVERSE mean to reverse the index programatically.

-
What do you mean by "however, I want to maintain one index instead." ? – Dr. belisarius Sep 29 '13 at 19:45
and why not just mm[[1 ;; ;; 2]]? – Pinguin Dirk Sep 29 '13 at 19:52
because k could be odd or even, if you do that way, you might miss the kth point if k is even. But your comment gives me some hint, I might be able to choose if I should use 1;; ;;2 or 2;; ;; 2 depends on if k is odd or even. Thanks anyway – user1285419 Sep 29 '13 at 19:57

You can reverse spans by

SpanReverse[Span[i_: 1, j_, k_: 1]] := Span[i + Floor[j - i, k], i, -k];

list = Range[11];
list[[1 ;; 5 ;; 2]]
SpanReverse[1 ;; 5 ;; 2]
list[[SpanReverse[1 ;; 5 ;; 2]]]

{1, 3, 5}
5 ;; 1 ;; -2
{5, 3, 1}


Spans can be joined only if they are aligned

SpanJoin[Span[i1_: 1, j1_, k_: 1], Span[i2_: 1, j2_: - 1, k_: 1]] :=
Span[i1, j2, k] /; i1 + Floor[j1 - i1, k] + k == i2;

SpanJoin[1 ;; 3 ;; 2, 5 ;; 11 ;; 2]

1 ;; 11 ;; 2


All together:

n = Length[list];
k = 3;
list[[SpanJoin[SpanReverse[k ;; 1 ;; -2], k + 2 ;; n ;; 2]]]

{1, 3, 5, 7, 9, 11}


P.S. In your particular case it is equivalent to

list[[;; ;; 2]]

{1, 3, 5, 7, 9, 11}

-
Thanks a lot. It works :) – user1285419 Sep 29 '13 at 19:48

I like to use Span when it works, but when I have to manipulate the order of indices, I prefer Table or Range. (combinations of ;; and , are difficult for me to read)

n = 11;
k = Ceiling[n/2];

M = Array["M", n];

idx1 = Table[i, {i, k, 1, -2}]~Join~Table[i, {i, k + 2, n, 2}]
idx2 = Reverse[Range[1, k, 2]]~Join~Range[k + 2, n, 2]
M[[idx1]]
M[[idx2]]

-

idx = Range[Mod[k,2,1], n, 2] seems to give what you want.

-