/*
* call-seq:
* array.shift -> obj or nil
* array.shift(n) -> array
*
* Returns the first element of <i>self</i> and removes it (shifting all
* other elements down by one). Returns <code>nil</code> if the array
* is empty.
*
* If a number _n_ is given, returns an array of the first n elements
* (or less) just like <code>array.slice!(0, n)</code> does.
*
* args = [ "-m", "-q", "filename" ]
* args.shift #=> "-m"
* args #=> ["-q", "filename"]
*
* args = [ "-m", "-q", "filename" ]
* args.shift(2) #=> ["-m", "-q"]
* args #=> ["filename"]
*/
static VALUE
rb_ary_shift_m(argc, argv, ary)
int argc;
VALUE *argv;
VALUE ary;
{
VALUE result;
long n;
if (argc == 0) {
return rb_ary_shift(ary);
}
rb_ary_modify_check(ary);
result = ary_shared_first(argc, argv, ary, Qfalse);
n = RARRAY(result)->len;
if (FL_TEST(ary, ELTS_SHARED)) {
RARRAY(ary)->ptr += n;
RARRAY(ary)->len -= n;
}
else {
MEMMOVE(RARRAY(ary)->ptr, RARRAY(ary)->ptr+n, VALUE, RARRAY(ary)->len-n);
RARRAY(ary)->len -= n;
}
return result;
}
1Note
Doesn't return nil on empty array when param is given
nhance ยท Apr 1, 20103 thanks
This does not return nil if the array is empty and n is given.
[].shift(2) # => []
a = []
a.shift(2) # => []
a # => []