shortcut for x = [x] unless x.is_a?(Array)

Sorry for double posting this on the Ruby section, I realized this is
kind of a rails question since it might relate to ActiveSupport.

Is there any prettier or cleaner way to write

x = [x] unless x.is_a?(Array)

I've looked into Array() and hash.to_a, but these will not give the
intended result as above.

Thanks in advance.

Aryk Grosz wrote:

Sorry for double posting this on the Ruby section, I realized this is
kind of a rails question since it might relate to ActiveSupport.

Is there any prettier or cleaner way to write

x = [x] unless x.is_a?(Array)

I've looked into Array() and hash.to_a, but these will not give the
intended result as above.

Thanks in advance.
  

I'm curious if someone can do better, but here's mine...

x = [x].flatten

disclaimer: won't give desired results on multi-dimensional arrays.

You can use Array().

a = [1]

=> [1]

b = 2

=> 2

Array(a)

=> [1]

Array(b)

=> [2]

  • Gabe

x = [*x]

Cheers-

- Ezra Zygmuntowicz
-- Founder & Software Architect
-- ezra@engineyard.com
-- EngineYard.com

Hey guys,

Thanks for the responses.

I don't think any of those quite work. Here is a sample from irb:

hash = {:x => {:y => :z}}

=> {:x=>{:y=>:z}}

[hash]

=> [{:x=>{:y=>:z}}] # what im trying to get

[*hash]

=> [[:x, {:y=>:z}]]

hash.to_a

=> [[:x, {:y=>:z}]]

Array(hash)

=> [[:x, {:y=>:z}]]

Now, if I was going to do hash.each {|k,v|}, i dont think this would
matter, but we can't assume thats always the case.

What does het asterisk mean? Never seen that before...

Hi --

What does het asterisk mean? Never seen that before...

It "unwraps" an array into a list of values.

array = [1,2,3]
[array] # => [[1,2,3]]
[*array] # => [1,2,3]

It also flows the other way, especially in method parameter syntax:

   def m(*args); end

   m(1,2,3)

The list 1,2,3 will be wrapped in the array args. The fact that args
is an array also means that it doesn't care whether or not it's empty.
Thus it represents optional arguments (unlike a plain parameter, which
doesn't already represent an object and therefore needs an argument
matched to it).

David

> x = [*x]

  > What does het asterisk mean? Never seen that before...

It's the splat operator.

See:
* http://ola-bini.blogspot.com/2006/11/nooks-and-crannies-of-ruby.html
* http://redhanded.hobix.com/bits/theSiphoningSplat.html
* http://redhanded.hobix.com/bits/wonderOfTheWhenBeFlat.html
* http://www.softiesonrails.com/2007/9/18/ruby-201-weird-hash-syntax

Alain

Hi --

I thought it was only used in method arguments... Thanks!

None of these methods, including the unarray operator seem to be doing
the trick:

hash = {:x => {:y => :z}}

=> {:x=>{:y=>:z}}

[hash]

=> [{:x=>{:y=>:z}}] # what im trying to get

[*hash]

=> [[:x, {:y=>:z}]]

hash.to_a

=> [[:x, {:y=>:z}]]

Array(hash)

=> [[:x, {:y=>:z}]]

All the other methods break up the hash into key/value pairs, I still
want the hash intact.

So are there any shortcuts for " x = [x] unless x.is_a?(Array) " when x
is a Hash?

Would it make sense to overwrite the #to_a function for Hash.

So instead of

h = { "c" => 300, "a" => 100, "d" => 400, "c" => 300 }
h.to_a » [["a", 100], ["c", 300], ["d", 400]]

It would be:

h = { "c" => 300, "a" => 100, "d" => 400, "c" => 300 }
h.to_a » [{ "c" => 300, "a" => 100, "d" => 400, "c" => 300 }]

What would this break? You can still do the hash.each{|k,v|} with this.
What am I missing?