如何优化这个IF MySQL查询

时间:2013-05-30 18:29:27

标签: mysql optimization

此MySQL查询需要6分钟才能运行。瓶颈是生成“活动已完成”列的最后一块。我把它写成子查询的原因是因为如果itemtype =“course”我需要为每个类中的每个用户找到所有其他项类型的MAX日期,而不是整个表列的MAX日期。我确信有更好的方法,但我不知道它是什么。任何人都可以帮助我吗?

SELECT DISTINCT 
  u.firstname AS 'First' , u.lastname AS 'Last', c.fullname AS 'Course', 
  IF (gi.itemtype = 'course', 
        CONCAT(c.fullname,"  COURSE TOTAL"), 
        gi.itemname) AS 'Item Name',

IFNULL(CONCAT(ROUND(gg.finalgrade,2),'/',ROUND(gi.grademax,2)), '0') 
  AS 'Points Earned',

IFNULL(CONCAT(ROUND((gg.finalgrade/gi.grademax),2)*100,'%'), '0%')
  AS 'Percentage',

(SELECT 
  IF(`Percentage`>=90, 'A', 
    IF(`Percentage`<90 AND `Percentage`>=80, 'B',
      IF(`Percentage`<80 AND `Percentage`>=70, 'C', 
        IF(`Percentage`<70 AND `Percentage`>=60, 'D', 'F'))))) 
  AS 'Grade',

IF(gi.itemtype = 'course',
  (SELECT 
     FROM_UNIXTIME(GREATEST(MAX(gg.timemodified), MAX(gg.timecreated)), 
                   '%m/%d/%Y')
   FROM mdl_course c
     JOIN mdl_grade_items gi
     JOIN mdl_grade_grades gg
   WHERE gg.userid=u.id 
     AND gi.courseid=c.id), 

   CASE 
     WHEN gg.timecreated IS NULL AND gg.timemodified IS NULL THEN '-'
     WHEN gg.timecreated IS NULL AND gg.timemodified IS NOT NULL THEN FROM_UNIXTIME(gg.timemodified, '%m/%d/%Y')
     WHEN gg.timecreated IS NOT NULL AND gg.timemodified IS NULL THEN FROM_UNIXTIME(gg.timecreated, '%m/%d/%Y')
     WHEN gg.timecreated<=gg.timemodified THEN FROM_UNIXTIME(gg.timemodified,'%m/%d/%Y')
   END)
  AS 'Activity Completed'

FROM mdl_user u
  JOIN mdl_user_enrolments ue on ue.userid=u.id
  JOIN mdl_enrol e ON e.id=ue.enrolid
  JOIN mdl_course c on c.id = e.courseid
  JOIN mdl_context AS ctx ON ctx.instanceid = c.id
  JOIN mdl_role_assignments AS ra ON ra.contextid = ctx.id
  JOIN mdl_role AS r ON r.id = e.roleid
  JOIN mdl_grade_items AS gi ON gi.courseid=c.id
  LEFT JOIN mdl_grade_grades AS gg ON gg.userid=u.id
    AND gg.itemid=gi.id

WHERE ue.status='0'
  AND gi.hidden = '0'
  AND gi.itemtype <> 'category'
  AND gg.excluded = '0'
  OR gg.excluded IS NULL

ORDER BY u.lastname, c.fullname, gi.itemtype DESC, gi.sortorder ASC

我希望输出看起来像这样:

First, Last, Course, Item Name, Points Earned, Percentage, Grade, Activity Completed
Test, Student1, Class1, Assignment 1, 10/10, 100%, A, 1/2/2013
Test, Student1, Class1, Assignment 2, 15/15, 100%, A, 3/4/2013
Test, Student1, Class1, Assignment 3, 0/15, 0%, F, -
Test, Student1, Class1, Class1 COURSE TOTAL, 25/40, 63%, D, 3/4/2013
Test, Student1, Class2, Assignment1, 20/30, 66%, D, 2/12/2013
Test, Student1, Class2, Assignment2, 1/5, 20%, F, 1/31/2013
Test, Student1, Class2, Class2 COURSE TOTAL, 21/35, 60%, D, 2/12/2013
Test, Student2, Class1, Assignment1, etc...

当我将EXPLAIN添加到查询中时,这就是我所得到的。 我无法复制列标题。他们是:

id, select_type, table, type, possible_keys, key, key_len, ref, rows, extra

1   PRIMARY u   ALL PRIMARY             449 Using temporary; Using filesort
1   PRIMARY ue  ref mdl_userenro_enruse_uix,mdl_userenro_enr_ix,mdl_userenro_use_ix mdl_userenro_use_ix 8   skol_dev.u.id   1   Using where
1   PRIMARY e   eq_ref  PRIMARY,mdl_enro_cou_ix PRIMARY 8   skol_dev.ue.enrolid 1   
1   PRIMARY r   eq_ref  PRIMARY PRIMARY 8   skol_dev.e.roleid   1   Using index
1   PRIMARY c   eq_ref  PRIMARY PRIMARY 8   skol_dev.e.courseid 1   
1   PRIMARY ctx ref PRIMARY,mdl_cont_ins_ix mdl_cont_ins_ix 8   skol_dev.c.id   1   Using where; Using index
1   PRIMARY gi  ref mdl_graditem_itenee_ix,mdl_graditem_cou_ix  mdl_graditem_cou_ix 9   skol_dev.e.courseid 7   Using where
1   PRIMARY ra  ref mdl_roleassi_con_ix mdl_roleassi_con_ix 8   skol_dev.ctx.id 4   Using index
1   PRIMARY gg  eq_ref  mdl_gradgrad_useite_uix,mdl_gradgrad_ite_ix,mdl_gradgrad_use_ix mdl_gradgrad_useite_uix 16  skol_dev.u.id,skol_dev.gi.id    1   Using where
3   DEPENDENT SUBQUERY  gg  ref mdl_gradgrad_useite_uix,mdl_gradgrad_use_ix mdl_gradgrad_use_ix 8   skol_dev.u.id   6   
3   DEPENDENT SUBQUERY  c   index   PRIMARY mdl_cour_cat_ix 8       124 Using index; Using join buffer
3   DEPENDENT SUBQUERY  gi  ref mdl_graditem_cou_ix mdl_graditem_cou_ix 9   skol_dev.c.id   7   Using where; Using index

0 个答案:

没有答案