Advanced Array Sorting in Ruby

Posted by Moser on 16 Sep 2008

While developing a member management application for my soaring club I found out quite a little about sorting arrays in Ruby. Rubys sort uses the operator <=>:

irb(main):001:0> 1 <=> 2
=> -1
irb(main):002:0> 1 <=> 0
=> 1
irb(main):003:0> 1 <=> 1
=> 0

By implementing it on your class you can specify a way in which an array of instances should be sorted. Here is a fragment of my Member class:

def <=>(b)
  name <=> b.name
end

My members will be sorted by their name. But sometimes you need a special sorting. Thats why the sort method accepts a block to specify a way of sorting

arr.sort! do |a, b|
  a.birthdate.yday <=> b.birthdate.yday
end

This is the sorting I needed for a list of birthdays. Sure enough you can do anything inside the block as long as it returns -1, 0 or 1. It’s no problem to sort by 2 attributes:

arr.sort! do |a, b|
  r = a.birthdate.yday <=> b.birtdate.yday
  r = a.name <=> b.name if r == 0
  r
end