array of hashes as hash key and value as array using jbuilder

1k Views Asked by At

I'm trying to generate JSON response using Jbuilder

I have an array of hashes like this

words=  [
      {"term": "abc",
      "definition": "123"
      } ,
      {"term": "abc",
       "definition": "345"
      } ,
      {"term": "xyz",
       "definition": "890"
      } 
   ]

I would like covert this into JSON. logic here is take all terms as keys and push it's definitions into arrays

  {
     "abc": ["123","345"],
     “xyz”: ["890"]
    }

What I achieved so far is

words.each do |word|  
  json.set! word['text'] ,word['definition']
end

gives me

{
  "abc": "123"   
  "abc": "345",
  "xyz": "890"
}

Could some help me on this.

4

There are 4 best solutions below

1
On BEST ANSWER

simplest solution :)

words=  [
      {"term": "abc",
      "definition": "123"
      } ,
      {"term": "abc",
       "definition": "345"
      } ,
      {"term": "xyz",
       "definition": "890"
      } 
   ]

result_hash = Hash.new{|hsh, key| hsh[key]=[] }
words.map{|x| result_hash[x[:term]].push(x[:definition])}

your output will be in result_hash

1
On

You are looking for something like this,

words =  [{:term=>"abc", :definition=>"123"}, {:term=>"abc", :definition=>"345"}, {:term=>"xyz", :definition=>"890"}]
words.inject({}) do |h, w|
  h[w[:term]] ||= []
  h[w[:term]] << w[:definition]
  h
end
#=> {"abc"=>["123", "345"], "xyz"=>["890"]}
0
On
words.group_by{|d| d[:term]}.map{|k,v| {k => v.map{|val| val[:definition]}}}.reduce(&:merge)
0
On
words.map(&:values).group_by(&:shift).each do |k, values|
  json.set! k, values.flatten
end

If the order of :term and :definition is not guaranteed, there is an intermediate call to .map(&:sort) on the original hash required, and :shift should be read as :pop since after sorting :definitions will preceed :terms.