0

I need to convert an array like this:

codes = ["AAAA 2.0", "BBBB 1.0", "CCCC n/a", "DDDD"]

into a hash like this:

codes = {
  "AAAA" => "2.0",
  "BBBB" => "1.0",
  "CCCC" => "n/a",
  "DDDD" => ""
}

Any thoughts how to handle this the best way?

2 Answers 2

8
hash = {}
codes.each { |a| hash[a.split[0]] = a.split[1].to_s }
hash
#=> {"AAAA"=>"2.0", "BBBB"=>"1.0", "CCCC"=>"n/a", "DDDD"=>""}

Alternatively (if you are ok with "" being nil):

Hash[codes.map(&:split)]
#=> {"AAAA"=>"2.0", "BBBB"=>"1.0", "CCCC"=>"n/a", "DDDD"=>nil}
Sign up to request clarification or add additional context in comments.

6 Comments

.map(&:split) looks better:)
yeah. I posted it as alternative solution because here "DDDD"=>nil.
Interesting that [["DDDD"]].to_h raises an error but Hash[["DDDD"]] works successfully
@shivam - thank you. I've used: codes_h = Hash[codes.map(&:split)] but got an error: "invalid number of elements (3 for 1..2) (Argument error)".
@msayen that will happen only when an element in codes has 3 words, which was not part of your question example.
|
1
codes.map { |s| s.split(/\s+/).tap { |a| a << "" if a.size==1 } }.to_h
  #=> {"AAAA"=>"2.0", "BBBB"=>"1.0", "CCCC"=>"n/a", "DDDD"=>""}

The steps are as follows.

codes.map { |s| s.split(/\s+/) }
  #=> [["AAAA", "2.0"], ["BBBB", "1.0"], ["CCCC", "n/a"], ["DDDD"]]

As we want to convert this to a hash, I would like to append an empty string to each of these arrays that are of size 1. Object#tap provides a convenient way of doing that:

b = codes.map { |s| s.split(/\s+/).tap { |a| a << "" if a.size==1 } }
  #=> [["AAAA", "2.0"], ["BBBB", "1.0"], ["CCCC", "n/a"], ["DDDD", ""]]

tap takes the result of s.split(/\s+/), represented by the block variable a and appends "" if it is of size 1. a is returned by tap, whether it has been altered or not. Lastly,

 b.to_h
   #=> {"AAAA"=>"2.0", "BBBB"=>"1.0", "CCCC"=>"n/a", "DDDD"=>""} 

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.