Reputation: 13
I have two active records StudentDemographics
and StudentWeeklyReport
both having has_many
relation like this:
class StudentDemographics < ActiveRecord::Base
has_many :student_weekly_reports, :foreign_key => :student_id
end
I have to check marks for each student in the last fifth week seminar with the latest one. If the result is true
, student should be active, else inactive. I have the following code. Here, I am repeating the loop with each date. @distinct
is an array of dates.
for i in [email protected]
active = 0
inactive = 0
sum = safe.length
@students = StudentDemographics.where("date <= ?", @distinct[i]).select("student_id") - safe
@students.each do |student|
@stu = StudentWeeklyReport.where(:student_id => student.student_id).select("student_id,golden_eggs").last(5)
if @stu.length > 4
if @stu[4].golden_eggs > @stu[0].golden_eggs
safe << student
active += 1
else
inactive += 1
end
else
safe << student
active += 1
end
end
@active[i] = active + sum
@inactive[i] = inactive
end
The performance is not good. It's taking more than 3 secs of time.my mysql db having 13600 in StudentWeeklyReports
table and 2000 in StudentDemographics
table. Can anyone suggest how to optimize the following code?
Upvotes: 0
Views: 118
Reputation: 5292
@students = StudentDemographics.includes(:student_weekly_reports).where("date <= ?", @distinct.min).select("student_id")
# The above line will fetch all the necessary records you require
for i in [email protected]
active = inactive = 0
@students = @student.select { |student_demographics| student_demographics.date <= @distinct[i] } - safe
@students.each do |student|
@stu = student.student_weekly_reports.select("golden_eggs").last(5)
if @stu.length > 4 and (@stu[4].golden_eggs <= @stu[0].golden_eggs)
inactive += 1
else
safe << student
active += 1
end
end
@active[i] = active + safe.length
@inactive[i] = inactive
end
Upvotes: 0
Reputation: 3709
@students = StudentDemographics.includes(:student_weekly_reports) - safe
for i in [email protected]
active = inactive = 0
@students.each do |student|
next if student.date > @distinct[i]
@stu = student.student_weekly_reports.select("golden_eggs").last(5)
if @stu.length > 4 && (@stu[4].golden_eggs <= @stu[0].golden_eggs)
inactive += 1
else
safe << student
active += 1
end
end
@active[i] = active + safe.length
@inactive[i] = inactive
end
Upvotes: 1