I have used LINQ in C# quite a while ago. The LINQ interface is quite user friendly, and I could write simple queries after seeing a few examples. At that time, I was quite ignorant of the N+1 problem, so I was not sure if I introduced any in the queries I composed.

The counterpart of LINQ in Rails world is active record, but I have never found it as smooth as LINQ, and I find myself always instantiating arrays way too often. Non-surprisingly, some pages on the website are quite slow. Decided to take this seriously, and really learn this active record stuff in Rails, I followed http://www.theodinproject.com/ruby-on-rails/active-record-queries and used ActiveRecord::QueryMethods on http://api.rubyonrails.org as the reference.

Rewriting two methods using the knowledge I acquired introduced 20x speedup for some queries, so it’s worth learning it in depth. I shall note down my understanding, which might be of some use for others.

Model.joins(:association).where("table_name.column" => value)

An potentially puzzling part could be the two namespace, active record models, and database tables. Inside joins, we are using the active record models, so that Model has a association called “association”, while inside where, we are using database namespace, so that the above example assumes that there’s a table called “table_name” with a column named “column”.

Another common confusion is between include and joins, and here’s my interpretation: include is used for eager loading so that late access of the association would not result into extra SQL queries, while joins is used for bringing other models into the namespace, so that following clauses (e.g. where) could reference them. In certain cases, one may want to do both, then:

Model.includes(:association).where("table_name.column" => value).references(:association)