多个JOINS - Mysql

时间:2013-11-16 13:45:17

标签: mysql

我有4张桌子:

类:

id  class   
1   X C     
2   VI B    
3   XII F   
4   X C     
5   VI B    
6   VIII A  

生:

    id  id_student  class   
    2   1 [->]      X C     
    3   4 [->]      VI B    
    5   7 [->]      X C     

等级

Id  id_student  grade   
3   1 [->]      8       
4   1 [->]      7       
5   1 [->]      10      
6   1 [->]      8       
7   1 [->]      9       
8   4 [->]      5       
9   4 [->]      7       
10  4 [->]      9   
11  1 [->]      4       
12  1 [->]      9       
13  7 [->]      10

缺勤:

id  id_student
1   1 [->]              
2   1 [->]              
3   1 [->]              
4   4 [->]              
5   1 [->]              
6   1 [->]              
7   1 [->]              
8   7 [->]   

我想要的是从课堂表中选择所有课程(只有那些有学生的课程)和 计算每个班级的学生人数,他们的成绩平均值和缺席人数。

这就是我所拥有的:

SELECT classes.class, COUNT(distinct students.id_students) AS nr_students, AVG(grades.grade) AS avg_grades
FROM classes 
    INNER JOIN students ON students.student = clases.class
    INNER JOIN grades ON students.students = grades.id_student
GROUP BY class

直到现在一切都很棒。输出(PHP):

Class  Nr_Students  Avg_Grades
VI B   1           7.0000    
X C    2           8.1250 

但我想从Absences表中计算每一行并打印每个班级的总缺席数。

这就是我要做的事情:

Class  Nr_Students  Avg_Grades  Nr_Abcences
VI B   1           7.0000       1
X C    2           8.1250       7

我无法更改数据库!

谢谢。

2 个答案:

答案 0 :(得分:1)

我怀疑某些列名和表名需要更改,因为您的查询根本不符合您的架构。以下是有效的:

SELECT s.class
    ,COUNT(s.id_student) AS nr_students
    ,g.avg_grade AS avg_grades
    ,SUM(a.cnt_absences) AS absences
FROM students s 
INNER JOIN (
    SELECT s.class, AVG(g.grade) AS avg_grade 
    FROM grades g
    INNER JOIN students s ON g.id_student = s.id_student
    GROUP BY s.class
  ) g ON s.class = g.class
LEFT JOIN (
    SELECT id_student, COUNT(id) AS cnt_absences 
    FROM absences  
    GROUP BY id_student
  ) a ON s.id_student = a.id_student
GROUP BY s.class, g.avg_grade

working on SQLFiddle

答案 1 :(得分:0)

仅提供子查询:

 SELECT classes.class, COUNT(distinct students.id_students) AS nr_students, AVG(grades.grade) AS avg_grades, COALESCE(ab.Nr_Abcences, 0)
    FROM classes 
        INNER JOIN students ON students.student = clases.class
        INNER JOIN note ON students.students = grades.id_student
        LEFT JOIN (SELECT class, COUNT(ab.id) AS NR_Abcences FROM Students INNER JOIN Absences ab ON ab.id_student = Students.id_student GROUP BY Students.class) ab ON ab.class = clases.class
    GROUP BY class

我没有测试此查询。