题解 | #统计复旦用户8月练题情况#
统计复旦用户8月练题情况
https://www.nowcoder.com/practice/53235096538a456b9220fce120c062b3
SELECT u.device_id, '复旦大学' AS university, SUM(CASE WHEN q.date is not null THEN 1 ELSE 0 END) AS question_cnt, SUM(if(q.result='right',1,0)) AS right_question_cnt FROM user_profile u LEFT JOIN question_practice_detail q USING (device_id) WHERE u.university = '复旦大学' AND (MONTH(q.date) = 8 OR q.date is NULL) GROUP BY u.device_id
0.题目要求刷过题和没有刷过题的信息都要显示,没有刷过题的同学刷题数目和正确刷题数目都为0.
1.这道题要注意device_id必须用u.device_id, 如果使用q.device_id,那么在显示结果时,有些没有刷过题的同学device_id是none。
2.用户表存放了学生的信息,并且是不重复的。question_practice_detail存放的是学生练习题目的信息,可能存在一个同学刷了多道题,但是不刷题目的同学信息在这个表中是显示不出来的。所以要用左连接,使得没有刷题的同学能在右表中显示NULL。
3.注意用SUM而不是COUNT,count是对记录数目的统计,如果用COUNT,则没有刷题的同学也会被算成1,用SUM是对1或者0的求和,符合题目
4.CASE WHEN和IF相当于一个字段,给每行都添加一个字段,只不过不显示出来,直接统计。例如对于每一条记录,如果结果正确,则记为1,否则记为0,最后根据分组求和。
5.SUM(CASE WHEN...) AS question_cnt这个字段,也可以通过COUNT(q.question_id)来计算,对于没有答题的同学,这个记录是NULL的,那么COUNT()出来就是0

