Uniq by object attribute in Ruby Uniq by object attribute in Ruby arrays arrays

Uniq by object attribute in Ruby


Use Array#uniq with a block:

@photos = @photos.uniq { |p| p.album_id }


Add the uniq_by method to Array in your project. It works by analogy with sort_by. So uniq_by is to uniq as sort_by is to sort. Usage:

uniq_array = my_array.uniq_by {|obj| obj.id}

The implementation:

class Array  def uniq_by(&blk)    transforms = []    self.select do |el|      should_keep = !transforms.include?(t=blk[el])      transforms << t      should_keep    end  endend

Note that it returns a new array rather than modifying your current one in place. We haven't written a uniq_by! method but it should be easy enough if you wanted to.

EDIT: Tribalvibes points out that that implementation is O(n^2). Better would be something like (untested)...

class Array  def uniq_by(&blk)    transforms = {}    select do |el|      t = blk[el]      should_keep = !transforms[t]      transforms[t] = true      should_keep    end  endend


Do it on the database level:

YourModel.find(:all, :group => "status")