let's say I have a model like this:
class Surface < ActiveRecord::Base
attr_accessible :width, :length
def area
self.width * self.length
end
end
Where @surface.area
returns the area of a surface. Now, lets say I have many surfaces called @surfaces
and I want to sum all areas. How do I do this?
My favorite solution would look like this:
@surfaces.sum(:area)
But it does not work. So how can I call .sum()
or .group()
or any similar functions on a virtual attributes like this in rails? I would like to avoid .each do |surface|
calls.
Thanks in advance.
sum
will quite happily accept an SQL expression instead of just a column name so all you need to do is translate your sum
method into SQL:
@surfaces.sum('width * height')
@surfaces.sum('surface.width * surface.height') # If you think other tables might be involved.
Also, class methods on your models are mixed into relations (since scopes and class methods are really the same thing) so you could add a class method to go with your instance method:
class Surface < ActiveRecord::Base
def self.area
sum('surface.width * surface.height')
end
def area
self.width * self.length
end
end
and say:
@surfaces.area
You're usually better off letting the database do the heavy lifting with your data, that's what they're for and what they're good at.