Maintenance Ruby 3.4 gets fixes, but no new features. Switch to Ruby 4.0 →
Array#values_at
static VALUE
rb_ary_values_at(int argc, VALUE *argv, VALUE ary)
{
long i, olen = RARRAY_LEN(ary);
VALUE result = rb_ary_new_capa(argc);
for (i = 0; i < argc; ++i) {
append_values_at_single(result, ary, olen, argv[i]);
}
RB_GC_GUARD(ary);
return result;
}
Returns elements from self in a new array; does not modify self.
The objects included in the returned array are the elements of self selected by the given specifiers, each of which must be a numeric index or a Range.
In brief:
a = ['a', 'b', 'c', 'd'] # Index specifiers. a.values_at(2, 0, 2, 0) # => ["c", "a", "c", "a"] # May repeat. a.values_at(-4, -3, -2, -1) # => ["a", "b", "c", "d"] # Counts backwards if negative. a.values_at(-50, 50) # => [nil, nil] # Outside of self. # Range specifiers. a.values_at(1..3) # => ["b", "c", "d"] # From range.begin to range.end. a.values_at(1...3) # => ["b", "c"] # End excluded. a.values_at(3..1) # => [] # No such elements. a.values_at(-3..3) # => ["b", "c", "d"] # Negative range.begin counts backwards. a.values_at(-50..3) # Raises RangeError. a.values_at(1..-2) # => ["b", "c"] # Negative range.end counts backwards. a.values_at(1..-50) # => [] # No such elements. # Mixture of specifiers. a.values_at(2..3, 3, 0..1, 0) # => ["c", "d", "d", "a", "b", "a"]
With no specifiers given, returns a new empty array:
a = ['a', 'b', 'c', 'd'] a.values_at # => []
For each numeric specifier index, includes an element:
-
For each non-negative numeric specifier
indexthat is in-range (less thanself.size), includes the element at offsetindex:Examplea.values_at(0, 2) # => ["a", "c"] a.values_at(0.1, 2.9) # => ["a", "c"]
-
For each negative numeric
indexthat is in-range (greater than or equal to- self.size), counts backwards from the end ofself:Examplea.values_at(-1, -4) # => ["d", "a"]
The given indexes may be in any order, and may repeat:
a.values_at(2, 0, 1, 0, 2) # => ["c", "a", "b", "a", "c"]
For each index that is out-of-range, includes nil:
a.values_at(4, -5) # => [nil, nil]
For each Range specifier range, includes elements according to range.begin and range.end:
-
If both
range.beginandrange.endare non-negative and in-range (less thanself.size), includes elements from indexrange.beginthroughrange.end - 1(ifrange.exclude_end?), or throughrange.end(otherwise):Examplea.values_at(1..2) # => ["b", "c"] a.values_at(1...2) # => ["b"]
-
If
range.beginis negative and in-range (greater than or equal to- self.size), counts backwards from the end ofself:Examplea.values_at(-2..3) # => ["c", "d"]
-
If
range.beginis negative and out-of-range, raises an exception:Examplea.values_at(-5..3) # Raises RangeError.
-
If
range.endis positive and out-of-range, extends the returned array withnilelements:Examplea.values_at(1..5) # => ["b", "c", "d", nil, nil]
-
If
range.endis negative and in-range, counts backwards from the end ofself:Examplea.values_at(1..-2) # => ["b", "c"]
-
If
range.endis negative and out-of-range, returns an empty array:Examplea.values_at(1..-5) # => []
The given ranges may be in any order and may repeat:
a.values_at(2..3, 0..1, 2..3) # => ["c", "d", "a", "b", "c", "d"]
The given specifiers may be any mixture of indexes and ranges:
a.values_at(3, 1..2, 0, 2..3) # => ["d", "b", "c", "a", "c", "d"]
Related: see Methods for Fetching.