SQL返回低分低于平均低分的数据?

时间:2018-03-17 15:08:19

标签: sql group-by having

我对家庭作业有疑问,我需要列出测验编号和评分低于平均低分的测验日期。

为此,我需要使用GROUP BY子句和HAVING子句。看起来应该是这样的:

select quiznum, quizdate
from quizzes
group by quiznum, quizdate, lowscore 
having lowscore < avg(lowscore);

然而,这不会返回任何数据。

如果我手动平均得分(大约是14),它会重新获得我需要的信息,但是对于这个问题,我不知道平均低分。

如何列出测验编号和低分低于平均低分的日期?

2 个答案:

答案 0 :(得分:0)

我猜这个查询可能适合你。

您需要创建一个子查询以获得avg分数。然后join自我并进行比较。

SELECT T2.* 
FROM 
(
    SELECT quiznum, 
       quizdate,
       avg(lowscore) as avgScore
    FROM quizzes
    group by quiznum, quizdate
) T1 INNER JOIN quizzes T2 
ON 
    T1.quiznum = T2.quiznum 
AND 
    T1.quizdate = T2.quizdate
Where T2.lowscore < T1.avgScore

答案 1 :(得分:0)

在这种情况下,我发现使用分析窗口函数更容易实现所需的输出。在我的查询中获取所需输出的键是:

AVG(score) OVER (PARTITION BY quiznum, quizdate) AS avg_score

使这项工作的查询如下。我使用WITH Clause来创建虚假数据但不要让您感到困惑。 BASE查询是您需要的。 WITH Clause就是在这里创建一个包含数据的假表。

WITH demo_data AS
(
  SELECT    1001     AS quiznum,    '10-JAN-18'  AS quizdate,   91   AS score    FROM dual UNION ALL
  SELECT    1001     AS quiznum,    '10-JAN-18'  AS quizdate,   75   AS score    FROM dual UNION ALL
  SELECT    1001     AS quiznum,    '10-JAN-18'  AS quizdate,   35   AS score    FROM dual UNION ALL
  SELECT    1001     AS quiznum,    '10-JAN-18'  AS quizdate,   40   AS score    FROM dual UNION ALL
  SELECT    1001     AS quiznum,    '10-JAN-18'  AS quizdate,   70   AS score    FROM dual UNION ALL
  SELECT    1001     AS quiznum,    '10-JAN-18'  AS quizdate,   85   AS score    FROM dual UNION ALL
  SELECT    1002     AS quiznum,    '17-JAN-18'  AS quizdate,   35   AS score    FROM dual UNION ALL
  SELECT    1002     AS quiznum,    '17-JAN-18'  AS quizdate,   40   AS score    FROM dual UNION ALL
  SELECT    1002     AS quiznum,    '17-JAN-18'  AS quizdate,   70   AS score    FROM dual UNION ALL
  SELECT    1002     AS quiznum,    '17-JAN-18'  AS quizdate,   85   AS score    FROM dual
)
SELECT quiznum, quizdate, score, avg_score
FROM
(
  SELECT quiznum, quizdate, score, AVG(score) OVER (PARTITION BY quiznum, quizdate) AS avg_score
  FROM demo_data
)
WHERE score < avg_score
;

下面的图片按测验编号和日期显示所有数据,并告诉我们平均分数。我们可以通过用外部Select包装它来使用它,这样我们就可以在WHERE子句中添加一个Filter,以便将Score与Average Score进行比较。

enter image description here

下一张图显示了在WHERE子句中添加过滤器后的样子:

enter image description here