同一行的平均值-SQL server

同一行的平均值-SQL server,sql,sql-server,average,Sql,Sql Server,Average,我有一个有5列的表。我需要找到每行使用SQL的平均值(忽略0列)。我能得到一些帮助吗 COL1 COL2 COL3 COL4 COL5 AVERAGE 1 2 3 4 5 3 4 0 4 0 4 4 3 0 0 0 9 6 7 0 0 0 0 7 对不起,桌子没有弄清楚。我需要为任何非零值的每一行计算平均值。例如:5个cols有(4,0,4,0,4)我不需要平均值为1

我有一个有5列的表。我需要找到每行使用SQL的平均值(忽略0列)。我能得到一些帮助吗

COL1 COL2 COL3 COL4 COL5 AVERAGE
  1    2    3   4     5   3
  4    0    4   0     4   4
  3    0    0   0     9   6
  7    0    0   0     0   7

对不起,桌子没有弄清楚。我需要为任何非零值的每一行计算平均值。例如:5个cols有(4,0,4,0,4)我不需要平均值为12/5,我需要平均值为12/3=4。基本上是除以非零值的数量。它并不总是被5除,这比第一眼看上去要复杂一些。在不使用透视表的情况下(这是另一种方法,但在这里可能有些过分),您可以对列求和,然后除以非零列的数量。诀窍是,当每列都为零时,您需要特别考虑到这一点,否则您将得到一个除以零的错误:

SELECT
  COL1, COL2, COL3, COL4, COL5,
  CASE WHEN (COL1 = 0 AND COL2 = 0 AND COL3 = 0 AND COL4 = 0 AND COL5 = 0) 
    THEN 0
    ELSE 
        (COL1 + COL2 + COL3 + COL4 + COL5)
        / (
            CASE WHEN COL1 = 0 THEN 0 ELSE 1 END +
            CASE WHEN COL2 = 0 THEN 0 ELSE 1 END +
            CASE WHEN COL3 = 0 THEN 0 ELSE 1 END +
            CASE WHEN COL4 = 0 THEN 0 ELSE 1 END +
            CASE WHEN COL5 = 0 THEN 0 ELSE 1 END
        )
    END AS AVERAGE
FROM stats

这比乍一看要复杂一些。在不使用透视表的情况下(这是另一种方法,但在这里可能有些过分),您可以对列求和,然后除以非零列的数量。诀窍是,当每列都为零时,您需要特别考虑到这一点,否则您将得到一个除以零的错误:

SELECT
  COL1, COL2, COL3, COL4, COL5,
  CASE WHEN (COL1 = 0 AND COL2 = 0 AND COL3 = 0 AND COL4 = 0 AND COL5 = 0) 
    THEN 0
    ELSE 
        (COL1 + COL2 + COL3 + COL4 + COL5)
        / (
            CASE WHEN COL1 = 0 THEN 0 ELSE 1 END +
            CASE WHEN COL2 = 0 THEN 0 ELSE 1 END +
            CASE WHEN COL3 = 0 THEN 0 ELSE 1 END +
            CASE WHEN COL4 = 0 THEN 0 ELSE 1 END +
            CASE WHEN COL5 = 0 THEN 0 ELSE 1 END
        )
    END AS AVERAGE
FROM stats

这里是另一个使用
交叉应用的选项。在计算平均数时,你必须谨慎而精确。例如,值1、1、2、2、3的预期平均值是多少
AVG
将返回1,但如果您希望它为1.8,则应在计算平均值之前使用浮点数据类型

with cte as (
    select * from
        (values
            (1, 2, 3, 4, 5)
            ,(4, 0, 4, 0, 4)
            ,(3, 0, 0, 0, 9)
            ,(7, 0, 0, 0, 0)
            ,(1, 1, 2, 2, 3)
        ) t(COL1, COL2, COL3, COL4, COL5)
)

select
    *
from
    cte
    cross apply (
        select 
            average = avg(val) --change to avg(val * 1.0) to get floating point numeric
        from 
            (values (COL1), (COL2), (COL3), (COL4), (COL5)) t(val) 
        where val > 0
    ) q

这里是另一个使用交叉应用的选项。在计算平均数时,你必须谨慎而精确。例如,值1、1、2、2、3的预期平均值是多少
AVG
将返回1,但如果您希望它为1.8,则应在计算平均值之前使用浮点数据类型

with cte as (
    select * from
        (values
            (1, 2, 3, 4, 5)
            ,(4, 0, 4, 0, 4)
            ,(3, 0, 0, 0, 9)
            ,(7, 0, 0, 0, 0)
            ,(1, 1, 2, 2, 3)
        ) t(COL1, COL2, COL3, COL4, COL5)
)

select
    *
from
    cte
    cross apply (
        select 
            average = avg(val) --change to avg(val * 1.0) to get floating point numeric
        from 
            (values (COL1), (COL2), (COL3), (COL4), (COL5)) t(val) 
        where val > 0
    ) q