3

I have the array of hash like this:

[{"1"=>{:name=>"Miss Sneaky", :race_no=>"2", :drawn_box=>"2"}}, {"1"=>{:name=>"Renny's Diggin'", :race_no=>"2", :drawn_box=>"3"}}, {"3"=>{:name=>"Fernando Hill", :race_no=>"2", :drawn_box=>"4"}}, {"2"=>{:name=>"Timely Fashion", :race_no=>"2", :drawn_box=>"6"}}, {"1"=>{:name=>"Federal Fletch", :race_no=>"2", :drawn_box=>"9"}}, {"2"=>{:name=>"Awesome Buddy", :race_no=>"4", :drawn_box=>"3"}}, {"7"=>{:name=>"Zipping Annabel", :race_no=>"4", :drawn_box=>"4"}}, {"4"=>{:name=>"Kylie Keeping", :race_no=>"4", :drawn_box=>"8"}}, {"5"=>{:name=>"Stent", :race_no=>"4", :drawn_box=>"1"}}, {"5"=>{:name=>"Jabeni", :race_no=>"4", :drawn_box=>"2"}}, {"11"=>{:name=>"Barsandi", :race_no=>"4", :drawn_box=>"6"}}, {"1"=>{:name=>"Little Prayer", :race_no=>"6", :drawn_box=>"2"}}, {"2"=>{:name=>"Charming Spirit", :race_no=>"6", :drawn_box=>"7"}}, {"4"=>{:name=>"Cawbourne Cooper", :race_no=>"6", :drawn_box=>"10"}}, {"2"=>{:name=>"Lagoon Alaska", :race_no=>"6", :drawn_box=>"4"}}, {"1"=>{:name=>"Bella Nineteen", :race_no=>"6", :drawn_box=>"5"}}, {"4"=>{:name=>"Annie Rocks", :race_no=>"6", :drawn_box=>"9"}}, {"1"=>{:name=>"Regent Tree", :race_no=>"8", :drawn_box=>"2"}}, {"1"=>{:name=>"Laughing Boy", :race_no=>"8", :drawn_box=>"7"}}, {"2"=>{:name=>"Smiley", :race_no=>"8", :drawn_box=>"8"}}, {"1"=>{:name=>"Sentosa Doll", :race_no=>"8", :drawn_box=>"9"}}, {"1"=>{:name=>"Propagandist", :race_no=>"8", :drawn_box=>"10"}}, {"2"=>{:name=>"Sakeyna", :race_no=>"3", :drawn_box=>"7"}}, {"2"=>{:name=>"King Kinloch", :race_no=>"3", :drawn_box=>"8"}}, {"2"=>{:name=>"Zipping Sherman", :race_no=>"3", :drawn_box=>"10"}}, {"3"=>{:name=>"Hard Case Watson", :race_no=>"3", :drawn_box=>"1"}}, {"3"=>{:name=>"Star Connie", :race_no=>"3", :drawn_box=>"2"}}, {"4"=>{:name=>"Ultimate Display", :race_no=>"3", :drawn_box=>"3"}}, {"5"=>{:name=>"Miss Milwaukee", :race_no=>"3", :drawn_box=>"5"}}, {"7"=>{:name=>"Duck And Dive", :race_no=>"3", :drawn_box=>"6"}}, {"1"=>{:name=>"Sentosa Doll", :race_no=>"3", :drawn_box=>"9"}}, {"2"=>{:name=>"My Sienna", :race_no=>"5", :drawn_box=>"1"}}, {"2"=>{:name=>"Simply Patches", :race_no=>"5", :drawn_box=>"6"}}, {"2"=>{:name=>"Sooky Lala", :race_no=>"5", :drawn_box=>"8"}}, {"3"=>{:name=>"Tiggerlong Pink", :race_no=>"5", :drawn_box=>"10"}}, {"5"=>{:name=>"Outside World", :race_no=>"5", :drawn_box=>"2"}}, {"1"=>{:name=>"Go Forward Bruno", :race_no=>"5", :drawn_box=>"3"}}, {"6"=>{:name=>"Zipping Anthea", :race_no=>"5", :drawn_box=>"5"}}, {"5"=>{:name=>"Simply Houdini", :race_no=>"5", :drawn_box=>"7"}}, {"3"=>{:name=>"Beauty's Girl", :race_no=>"5", :drawn_box=>"9"}}, {"3"=>{:name=>"Ziggy Stardust", :race_no=>"7", :drawn_box=>"1"}}, {"7"=>{:name=>"Flashing Oscar", :race_no=>"7", :drawn_box=>"2"}}, {"5"=>{:name=>"Kurios Motion", :race_no=>"7", :drawn_box=>"3"}}, {"7"=>{:name=>"Kermaro", :race_no=>"7", :drawn_box=>"4"}}, {"6"=>{:name=>"Tap Out Lucy", :race_no=>"7", :drawn_box=>"5"}}, {"10"=>{:name=>"Zipping Benson", :race_no=>"7", :drawn_box=>"6"}}, {"24"=>{:name=>"Fire Legend", :race_no=>"7", :drawn_box=>"7"}}, {"8"=>{:name=>"Dashing Display", :race_no=>"7", :drawn_box=>"8"}}, {"2"=>{:name=>"Rattlin' Home", :race_no=>"9", :drawn_box=>"1"}}, {"3"=>{:name=>"Byron Breeze", :race_no=>"9", :drawn_box=>"3"}}, {"5"=>{:name=>"Shafted", :race_no=>"9", :drawn_box=>"4"}}, {"8"=>{:name=>"Eva's Girl", :race_no=>"9", :drawn_box=>"5"}}, {"6"=>{:name=>"Blazin' Sophia", :race_no=>"9", :drawn_box=>"6"}}, {"7"=>{:name=>"Enjoy Yourself", :race_no=>"9", :drawn_box=>"7"}}, {"3"=>{:name=>"General George", :race_no=>"9", :drawn_box=>"8"}}, {"2"=>{:name=>"Zipping Sherman", :race_no=>"9", :drawn_box=>"9"}}, {"1"=>{:name=>"Teeny Tiger", :race_no=>"10", :drawn_box=>"4"}}, {"2"=>{:name=>"Tiggerlong Blaze", :race_no=>"10", :drawn_box=>"7"}}, {"1"=>{:name=>"Propagandist", :race_no=>"10", :drawn_box=>"9"}}, {"1"=>{:name=>"Sentosa Doll", :race_no=>"10", :drawn_box=>"10"}}, {"1"=>{:name=>"Fascinate Hannah", :race_no=>"10", :drawn_box=>"1"}}, {"4"=>{:name=>"Olivia's Chance", :race_no=>"10", :drawn_box=>"2"}}, {"2"=>{:name=>"Prelious Jade", :race_no=>"10", :drawn_box=>"3"}}, {"1"=>{:name=>"Still Laughing", :race_no=>"10", :drawn_box=>"5"}}]

want to group with the key example: {"1"=> , "2"=> etc..

I have tried this

wins.group_by { |h| h.keys.first }.sort.reverse.to_h

I am getting the result like

{"8"=>[{"8"=>{:name=>"Dashing Display", :race_no=>"7", :drawn_box=>"8"}}, {"8"=>{:name=>"Eva's Girl", :race_no=>"9", :drawn_box=>"5"}}], "7"=

but I need a response like

{"8"=>[{:name=>"Dashing Display", :race_no=>"7", :drawn_box=>"8"}, {:name=>"Eva's Girl", :race_no=>"9", :drawn_box=>"5"}], etc ...

How can I get the expected response?

1
  • In future please make your examples as small as possible while retaining all essential elements of the question. Here you might have limited your array to, say, four hashes (rather than 64!). It is also helpful to format objects so that they can be read without the need for horizontal scrolling and to assign a variable to all inputs (e.g., arr = [ {"1"=>{:name=>"Miss Sneaky",...) so that readers can refer to those variables in answers and comments without having to define them. (Note "64!" is not to be read "64 factorial"). Commented Sep 21, 2021 at 8:49

3 Answers 3

3

If arr is the array of hashes given in the question's example, one can write the following:

f = arr.each_with_object(Hash.new { |h,k| h[k] = [] }) do |g,h|
  k,f = g.flatten
  h[k] << f
end

When, for example,

g = {"8"=>{:name=>"Dashing Display", :race_no=>"7", :drawn_box=>"8"}}

k,f = g.flatten
  #=> ["8", {:name=>"Dashing Display", :race_no=>"7", :drawn_box=>"8"}]
k #=> "8" 
f #=> {:name=>"Dashing Display", :race_no=>"7", :drawn_box=>"8"}

See Hash#flatten.

I assume the order of the keys in the hash that is returned is unimportant. I further assume that the order of the hashes in the arrays that are the values of those keys is also unimportant.

This uses the form of Hash::new that has a block but no argument. When h has no key k this causes h[k] = [] to be executed immediately before h[k] << f is executed.

We find, for example:

f['8']
  #=> [{:name=>"Dashing Display", :race_no=>"7", :drawn_box=>"8"},
  #    {:name=>"Eva's Girl", :race_no=>"9", :drawn_box=>"5"}]

The corresponding elements (hashes) of arr that have a key '8' are as follows:

arr.select { |h| h.keys == ["8"] }
  #=> [{"8"=>{:name=>"Dashing Display", :race_no=>"7", :drawn_box=>"8"}},
  #    {"8"=>{:name=>"Eva's Girl", :race_no=>"9", :drawn_box=>"5"}}]

​ The calculation of f is seen to produce the desired result.

Sign up to request clarification or add additional context in comments.

Comments

1

you can write your own custom logic to achieve above grouping. Something like below:

result = {}
input.each do |element|
  key = element.keys.first
  result.merge!(key => (result[key] || []) << element[key])
end
result

And later on sort this based on your requirement.

1 Comment

You may wish to remove the first and last lines and replace the second line with input.each_with_object({}) do |element, result|.
1

So if we take your current result:

result1 = wins.group_by { |h| h.keys.first }.sort.reverse.to_h

Now the keys are strings like "8", and the values are lists of hashes.

All we want to do here is take those lists of hashes, and for each of them, simply extract the first value, because we know they each only have one value.

To do this:

result2 = result1.transform_values do |list_of_hashes|
  list_of_hashes.map { |hash| hash.values.first }
end

Another approach would be to just process the whole thing with reduce:

result = wins.reduce({}) do |memo, hash|
  key = hash.keys.first
  memo[key] ||= []
  memo[key].push hash.values.first
  memo
end.sort.reverse

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.