A splat on a hash converts it into an array.
[*{foo: :bar}] # => [[:foo, :bar]]
Is there some hidden mechanism (such as implicit class cast) going on here, or is it a built-in primitive feature?
Besides an array, are
nil
and hash the only things that disappear/change with the splat operator under Ruby 1.9?
Asked
Active
Viewed 5,215 times
12

sawa
- 165,429
- 45
- 277
- 381
1 Answers
15
A splat will attempt an explicit conversion of an object to an Array.
To do this, it will send to_a
and expect an Array
as a result.
class Foo
def to_a
[1,2,3]
end
end
a, b, c = *Foo.new
a # => 1
If the object does not respond to to_a
, then there is no effect, e.g. [*42] == [42]
Many builtin classes implement to_a
. In particular:
- (because they include
Enumerable
)Array
Hash
Range
IO
andFile
Enumerator
Enumerator::Lazy
(Ruby 2.0)Set
andSortedSet
- (additional classes)
NilClass
MatchData
OpenStruct
Struct
Time
Matrix
andVector
All these can thus be splatted:
match, group, next_group = *"Hello, world".match(/(.*), (.*)/)
group # => "Hello"

Marc-André Lafortune
- 78,216
- 16
- 166
- 166
-
1Splatted `nil` disappears Under Ruby 1.9, and this does not fit the case of there being no effect, so this is the only exception, I guess. Am I right? – sawa Jan 14 '13 at 11:20
-
2Oh, forgot about `nil`. Edited answer. `NilClass` implements `to_a` (by returning `[]`), so it's not a special case. No effect would mean that `[*nil]` would be `[nil]` instead of `[]` – Marc-André Lafortune Jan 14 '13 at 20:35