SQL SUM/AVG 查询排除 postgres 中的行
SQL SUM/AVG query exclude rows in postgres
我有一个 table 存储问卷结果。 table 的列名为:
q1,q2,q3,q4 ....
有效值为 0 到 100 之间的正数。如果未回答问题,则值为 -1,因此我以行结尾:
q1 q2 q3 q4 ...
row 1 10 100 -1 50
row 2 20 -1 20 20
row 3 50 60 100 -1
我想汇总 q1 到 q4,结果如下:
总和:
q1 => 80
q2 => 160
q3 => 120
q4 => 70
平均:
q1 => 80 / 3
q2 => 160 / 2
q3 => 120 / 2
q4 => 70 / 2
我怎样才能做到这一点?
SQL 未针对像这样的每一列的平均值进行优化。它更适合行分组。但是,您可以通过为每一列手动编写这样的条件数据透视语句来解决此问题:
SELECT
SUM(CASE WHEN q1 > 0 THEN q1 ELSE 0 END)/
SUM(CASE WHEN q1 > 0 THEN 1 ELSE 0 END) AS q1_avg,
SUM(CASE WHEN q2 > 0 THEN q1 ELSE 0 END)/
SUM(CASE WHEN q2 > 0 THEN 1 ELSE 0 END) AS q2_avg
FROM table;
只需将 -1
替换为 NULL
并直接在列上使用聚合函数:
SELECT sum(q1) AS q1_sum
, sum(q2) AS q2_sum
, sum(q3) AS q3_sum
, sum(q4) AS q4_sum
, count(q1) AS q1_ct
, count(q2) AS q2_ct
, count(q3) AS q3_ct
, count(q4) AS q4_ct
, round(avg(q1),2) AS q1_avg
, round(avg(q2),2) AS q2_avg
, round(avg(q3),2) AS q3_avg
, round(avg(q4),2) AS q4_avg
FROM (
SELECT NULLIF(q1, -1) AS q1
, NULLIF(q2, -1) AS q2
, NULLIF(q3, -1) AS q3
, NULLIF(q4, -1) AS q4
FROM tbl
) t;
为什么?
NULL 值会自动从所有这些聚合函数中排除。
将不存在的值存储为 NULL 开始会更简单。
我有一个 table 存储问卷结果。 table 的列名为:
q1,q2,q3,q4 ....
有效值为 0 到 100 之间的正数。如果未回答问题,则值为 -1,因此我以行结尾:
q1 q2 q3 q4 ...
row 1 10 100 -1 50
row 2 20 -1 20 20
row 3 50 60 100 -1
我想汇总 q1 到 q4,结果如下:
总和:
q1 => 80
q2 => 160
q3 => 120
q4 => 70
平均:
q1 => 80 / 3
q2 => 160 / 2
q3 => 120 / 2
q4 => 70 / 2
我怎样才能做到这一点?
SQL 未针对像这样的每一列的平均值进行优化。它更适合行分组。但是,您可以通过为每一列手动编写这样的条件数据透视语句来解决此问题:
SELECT
SUM(CASE WHEN q1 > 0 THEN q1 ELSE 0 END)/
SUM(CASE WHEN q1 > 0 THEN 1 ELSE 0 END) AS q1_avg,
SUM(CASE WHEN q2 > 0 THEN q1 ELSE 0 END)/
SUM(CASE WHEN q2 > 0 THEN 1 ELSE 0 END) AS q2_avg
FROM table;
只需将 -1
替换为 NULL
并直接在列上使用聚合函数:
SELECT sum(q1) AS q1_sum
, sum(q2) AS q2_sum
, sum(q3) AS q3_sum
, sum(q4) AS q4_sum
, count(q1) AS q1_ct
, count(q2) AS q2_ct
, count(q3) AS q3_ct
, count(q4) AS q4_ct
, round(avg(q1),2) AS q1_avg
, round(avg(q2),2) AS q2_avg
, round(avg(q3),2) AS q3_avg
, round(avg(q4),2) AS q4_avg
FROM (
SELECT NULLIF(q1, -1) AS q1
, NULLIF(q2, -1) AS q2
, NULLIF(q3, -1) AS q3
, NULLIF(q4, -1) AS q4
FROM tbl
) t;
为什么?
NULL 值会自动从所有这些聚合函数中排除。
将不存在的值存储为 NULL 开始会更简单。