Sort an array based on an attribute of its objects

J

Joshua Muheim

Hi all

The title of this topic is not very good, but I didn't really know how
to describe it in just a few words...

So here is what I need to do:

I have a array of some objects:

[obj1, obj2, obj3, obj4]

All objects have a method "status" that returns a status object, like
"open", "request", "cancelled", "completed" etc.

Now I'd like to sort the elements after theses statuses into a new hash,
so in the end it should look something like this:

{status1 => [obj1, obj3],
status3 => [obj2],
status4 => [obj4]}

I need this because I want then to iterate through the hash and display
an HTML list grouped by status:

<ul>
<li>
Request:
<ul>
<li>Object 1</li>
<li>Object 3</li>
</ul>
</li>
<li>
Cancelled:
<ul>
<li>Object 2</li>
</ul>
</li>
... and so on...
</ul>

What's an elegant way to do this? :)

Thanks a lot,
Josh
 
D

David A. Black

Hi --

Hi all

The title of this topic is not very good, but I didn't really know how
to describe it in just a few words...

So here is what I need to do:

I have a array of some objects:

[obj1, obj2, obj3, obj4]

All objects have a method "status" that returns a status object, like
"open", "request", "cancelled", "completed" etc.

Now I'd like to sort the elements after theses statuses into a new hash,
so in the end it should look something like this:

{status1 => [obj1, obj3],
status3 => [obj2],
status4 => [obj4]}

I need this because I want then to iterate through the hash and display
an HTML list grouped by status:

<ul>
<li>
Request:
<ul>
<li>Object 1</li>
<li>Object 3</li>
</ul>
</li>
<li>
Cancelled:
<ul>
<li>Object 2</li>
</ul>
</li>
... and so on...
</ul>

What's an elegant way to do this? :)

In Ruby 1.9 you can do:

array.group_by {|obj| obj.status }

and get a hash. If you need to roll your own:

class Array
def group_by
hash = Hash.new {|h,k| h[k] = [] }
each {|e| hash[yield(e)] << e }
hash
end
end

(or in a module, or whatever).


David
 
R

Robert Dober

David beat me to the line, but as somebody will post an inject based
solution anyway, why not let it be me ;).

class Array
def group_by message = nil
inject( Hash.new {|h,k| h[k] = [] } ){ |h, e|
h[message ? e.send( message ) : yield(e)] << e
h
}
end
end


p %w{ Hello Brave GNU World }.group_by {|o| o.size }
p %w{ Hello Brave GNU World }.group_by( :size )

Cheers
Robert
 
X

Xavier Noria

I have a array of some objects:

[obj1, obj2, obj3, obj4]

All objects have a method "status" that returns a status object, like
"open", "request", "cancelled", "completed" etc.

Now I'd like to sort the elements after theses statuses into a new hash,
so in the end it should look something like this:

{status1 => [obj1, obj3],
status3 => [obj2],
status4 => [obj4]}

If working with a Set is fine (there's #to_set) that's provided by Set#classify.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,580
Members
45,054
Latest member
TrimKetoBoost

Latest Threads

Top