1

I am just learning Ruby and started working with arrays. I have an array that looks like:

easyStats = [<SampleArray: @id=0, @stats=#<OpenStruct total_sessions_played=244, total_sessions_lost=124>>, 
             <SampleArray: @id=1, @stats=#<OpenStruct total_sessions_played=204, total_sessions_lost=129>>, 
             <SampleArray: @id=2, @stats=#<OpenStruct total_sessions_played=2, total_sessions_lost=4>>]

I can sort the array by the id (Integer) attribute as such:

easyStats.sort_by(&:id)

However, what I would like to do is sort the array by a key of the OpenStruct object, I have tried the following options with different errors:

easyStats.sort_by(&:stats)

Error: comparison of OpenStruct with OpenStruct failed

easyStats.sort_by(&:stats[:total_sessions_played])

Error: no implicit conversion of Symbol into Integer

easyStats[:stats].sort_by(&:total_sessions_played)

Error: no implicit conversion of Symbol into Integer

I have seen solutions on how to sort an array of just one OpenStruct object and I think I understand it - How to sort a ruby array by two conditions

Could someone show me how to sort by any key of the OpenStruct object in this example (Array with Integer and OpenStruct objects)?

2 Answers 2

4

The sort_by method takes a block and uses the return value of that block as the key to sort by. In your case, you can access that value by doing:

easyStats.sort_by { |i| i.stats.total_sessions_played }

The .sort_by(&:key) code is really just shorthand for .sort_by { |i| i.key }. And you can only use it when the block consists of a single method called on the block argument. You can read more about how and why it works here.

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

Comments

2

You should provide an actual block (since you are calling two methods on each item consecutively):

easyStats.sort_by{|x| x.stats.total_sessions_played}

So you can't really use a short notation with & here.

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.