# Splitting a list at a particular position

Is it possible to split a list into two lists at a specific position? The main list is for example:

data={{xa,ya},{xb,yb},{xc,yc},...,{xz,yz}}.


I want to split this list into two new lists:

data1={{xa,ya},{xb,yb},...,{xi,yi}}


and

data2={{xj,yj},{xk,yk},...,{xz,yz}}


at a specific y-value at position i. I was not successful in using Part. Maybe there is another possibility?

This can be accomplished easily using Part ([[ ]]) and Span (;;), as follows:

data = {{x1, y1}, {x2, y2}, {x3, y3}, {x4, y4}, {xz, yz}};
data[[;; 3]]
data[[4 ;;]]

(* ->
{{x1, y1}, {x2, y2}, {x3, y3}}
{{x4, y4}, {xz, yz}}
*)

• You beat me to it, so I added my answer to yours. May 5, 2012 at 19:34
• If you don't want Part[], there's always Take[]... May 5, 2012 at 19:43

Following up on J.M.'s suggestion,

m = 3;
data1 = Take[data, m]
data2 = Take[data, -(Length[data] - m)]


You might also obtain data2 as follows:

data2 = Complement[data, data1]


I'm uncertain whether the second approach would maintain order invariant if there are identical sublists.

• Or, perhaps, {Take[#, 3], Drop[ #, 3]} &@data May 5, 2012 at 22:58
• Surprisingly this is faster than Part as recommended by belisarius, and considerably faster than Take/Drop as recommended by Tom. It could also be written: {Take[data, m], Take[data, {m + 1, -1}]} with about the same performance. May 6, 2012 at 0:01
• I'm surprised it's faster than Take...Drop. May 6, 2012 at 0:32

Starting from 10.2 you can use TakeDrop

data = {{x1, y1}, {x2, y2}, {x3, y3}, {x4, y4}, {xz, yz}};

{data1, data2} = TakeDrop[data, 3]
(* {{{x1, y1}, {x2, y2}, {x3, y3}}, {{x4, y4}, {xz, yz}}} *)