2010-03-02 48 views
3

所以我有3個不同的列(籃子1,2和3)。有時候這些列有所有的信息,有時候其中有一兩個是空的。我有另一個欄目,我將把這些值平均並保存。帶NULL的MS-SQL平均列

是否有一種圓滑/簡單的方法來獲得這三列的平均值,即使其中一個爲空?或者我必須爲每一個爲空的特殊檢查?

實例數據(~~爲null)

- B1 - B2 - B3 - Avg 
------------------------------ 
- 10 - 20 - 30 - 20 
- 10 - ~~ - 30 - 20 
- ~~ - 20 - ~~ - 20 

我怎麼會寫在T-SQL來更新我的臨時表?

UPDATE @MyTable 
    SET Avg = ??? 

答: 感謝Aaronaught爲我所用的方法。我會把我的代碼放在這裏,以防其他人擁有相同的東西。

WITH AverageView AS 
(
    SELECT Results_Key AS xxx_Results_Key, 
      AVG(AverageValue) AS xxx_Results_Average 
    FROM @MyResults 
     UNPIVOT (AverageValue FOR B IN (Results_Basket_1_Price, Results_Basket_2_Price, Results_Basket_3_Price)) AS UnpivotTable 
    GROUP BY Results_Key 
) 
UPDATE @MyResults 
    SET Results_Baskets_Average_Price = xxx_Results_Average 
    FROM AverageView 
    WHERE Results_Key = xxx_Results_Key; 
+0

您使用哪種RDBMS? – Quassnoi 2010-03-02 22:59:25

回答

4

假設你有某種ID列的,最有效的辦法可能是使用UNPIVOT這樣你就可以使用正常的基於行的AVG運營商(而忽略NULL值):

DECLARE @Tbl TABLE 
(
    ID int, 
    B1 int, 
    B2 int, 
    B3 int 
) 

INSERT @Tbl (ID, B1, B2, B3) VALUES (1, 10, 20, 30) 
INSERT @Tbl (ID, B1, B2, B3) VALUES (2, 10, NULL, 30) 
INSERT @Tbl (ID, B1, B2, B3) VALUES (3, 10, NULL, NULL) 

SELECT ID, AVG(Value) AS Average 
FROM @Tbl 
UNPIVOT (Value FOR B IN (B1, B2, B3)) AS u 
GROUP BY ID 

如果沒有ID列,您可以使用ROW_NUMBER產生替代ID:

;WITH CTE AS 
(
    SELECT 
     B1, B2, B3, 
     ROW_NUMBER() OVER (ORDER BY (SELECT 1)) AS ID 
    FROM @Tbl 
) 
SELECT ID, AVG(Value) 
FROM CTE 
UNPIVOT (Value FOR B IN (B1, B2, B3)) AS u 
GROUP BY ID 
+0

+1,但請注意,這使用非標準擴展名。 – 2010-03-02 23:03:59

+0

完美,這正是我所需要的 – Miles 2010-03-02 23:17:22

1
SELECT (
     SELECT AVG(b) 
     FROM (
       SELECT b1 AS b 
       UNION ALL 
       SELECT b2 
       UNION ALL 
       SELECT b3 
       ) q 
     ) 
FROM mytable 
0
SELECT (ISNULL(B1,0) + ISNULL(B2,0) + ISNULL(B3,0)) 
/(CASE WHEN B1 IS NULL THEN 0 ELSE 1 END 
+CASE WHEN B2 IS NULL THEN 0 ELSE 1 END 
+CASE WHEN B3 IS NULL THEN 0 ELSE 1 END) 

並將邏輯放在那裏以排除所有三個都爲空的情況,如果需要的話。