SQL 使用 CASE 计算值

SQL Calculating Values Using CASE

我正在使用 CASE 根据产品类别计算商品的总重量。

为此,我使用代码:

CASE WHEN [PC].[ProductCategoryCode] = 5870 THEN SUM(SUM([PL].[OriginalQuantity_Stk])) OVER (PARTITION BY [PC].[ProductCategoryCode]) 
WHEN [PC].[ProductCategoryCode] = 5730 THEN SUM(SUM([PL].[OriginalQuantity_Stk])) OVER (PARTITION BY [PC].[ProductCategoryCode])
WHEN [PC].[ProductCategoryCode] = 5990 THEN SUM(SUM([PL].[OriginalQuantity_Stk])) OVER (PARTITION BY [PC].[ProductCategoryCode])
ELSE SUM(SUM([PL].[OriginalQuantity_Stk])) OVER()
END
 AS [Total Weight]

5870、5730、5990都显示正确的总重量。问题出在 ELSE 部分。其余值都有不同的产品类别代码,但需要将它们组合在一起,我需要这些值的总重量。目前,ELSE部分取所有项目的总和,包括产品5870、5730、5990。

例如:

Product Category Code | Weight |
5870                  | 100    |
5730                  | 400    |
5990                  | 200    |
1111                  | 50     |  
2222                  | 175    |  
3333                  | 500    |  
4444                  | 125    |  

5870 = 100
5730 = 400
5990 = 200
ELSE = 850

完整代码:

SET NOCOUNT ON; 
DECLARE @Credits Decimal(19,8);
DECLARE @Price Decimal(19,8);

SET @Credits = 41000;
SET @Price = 1.57;

SELECT 
     CASE WHEN [PC].[ProductCategoryCode] = 5870 THEN 'Trimmings' 
WHEN [PC].[ProductCategoryCode] = 5730 THEN 'Rib Tips'
WHEN [PC].[ProductCategoryCode] = 5990 THEN 'Skins'
ELSE [PC].[Description1] 
END AS [Description]
   , CASE WHEN [PC].[ProductCategoryCode] = 5870 THEN SUM(SUM([PL].[OriginalQuantity_Stk])) OVER (PARTITION BY [PC].[ProductCategoryCode]) 
WHEN [PC].[ProductCategoryCode] = 5730 THEN SUM(SUM([PL].[OriginalQuantity_Stk])) OVER (PARTITION BY [PC].[ProductCategoryCode])
WHEN [PC].[ProductCategoryCode] = 5990 THEN SUM(SUM([PL].[OriginalQuantity_Stk])) OVER (PARTITION BY [PC].[ProductCategoryCode])
ELSE SUM(SUM([PL].[OriginalQuantity_Stk])) OVER()
END
 AS [Total Weight]
   , Sum(CASE WHEN [PC].[ProductCategoryCode] <> 5870 THEN [PL].[OriginalQuantity_Stk] 
WHEN [PC].[ProductCategoryCode] <> 5730 THEN [PL].[OriginalQuantity_Stk] 
WHEN [PC].[ProductCategoryCode] <> 5990 THEN [PL].[OriginalQuantity_Stk] 
END) AS [Weight]
   , @Credits - SUM(Sum([PL].[OriginalQuantity_Stk])) OVER () AS [Shrink]
   , CASE WHEN [PC].[ProductCategoryCode] = 5870 THEN SUM(Sum([PL].[OriginalQuantity_Stk]) / @Credits) OVER (PARTITION BY [PC].[ProductCategoryCode]) 
WHEN [PC].[ProductCategoryCode] = 5730 THEN SUM(Sum([PL].[OriginalQuantity_Stk]) / @Credits) OVER (PARTITION BY [PC].[ProductCategoryCode])
WHEN [PC].[ProductCategoryCode] = 5990 THEN SUM(Sum([PL].[OriginalQuantity_Stk]) / @Credits) OVER (PARTITION BY [PC].[ProductCategoryCode])
ELSE Sum([PL].[OriginalQuantity_Stk]) / @Credits
END AS [Yield]
   , CASE WHEN [PC].[ProductCategoryCode] = 5870 THEN [ICP].[UnitCost] 
WHEN [PC].[ProductCategoryCode] = 5730 THEN [ICP].[UnitCost] - 0.25 
WHEN [PC].[ProductCategoryCode] = 5990 THEN [ICP].[UnitCost] * 0 
ELSE [ICP].[UnitCost]
END AS [UC]
   , CASE WHEN [PC].[ProductCategoryCode] = 5870 THEN [ICP].[UnitCost] * SUM(Sum([PL].[OriginalQuantity_Stk]) / @Credits) OVER (PARTITION BY [PC].[ProductCategoryCode])
WHEN [PC].[ProductCategoryCode] = 5730 THEN ([ICP].[UnitCost] - 0.25) * SUM(Sum([PL].[OriginalQuantity_Stk]) / @Credits) OVER (PARTITION BY [PC].[ProductCategoryCode])
WHEN [PC].[ProductCategoryCode] = 5990 THEN ([ICP].[UnitCost] * 0) * SUM(Sum([PL].[OriginalQuantity_Stk]) / @Credits) OVER (PARTITION BY [PC].[ProductCategoryCode])
ELSE [ICP].[UnitCost] * SUM(Sum([PL].[OriginalQuantity_Stk]) / @Credits) OVER (PARTITION BY [PC].[ProductCategoryCode])
END AS [Value]
   , CASE WHEN [PC].[ProductCategoryCode] = 5780 OR [PC].[ProductCategoryCode] < 5700 THEN SUM(Sum([PL].[OriginalQuantity_Stk]) / @Credits * [ICP].[UnitCost])
OVER (PARTITION BY [PC].[ProductCategoryCode])
END AS [TotalValue]
 FROM (((( IC_Products [PC] 
    INNER JOIN  DC_Transactions [DCT] 
     ON [PC].ProductKey = [DCT].ProductKey)
    INNER JOIN  AR_Customers [ARC] 
     ON [DCT].CustomerKey = [ARC].CustomerKey)
    INNER JOIN  IC_ProductLots [PL] 
     ON [DCT].LotKey = [PL].LotKey)
    LEFT OUTER JOIN  IC_ProductCosts [ICP] 
     ON ICP.ProductKey=PC.ProductKey and ICP.ProductCostCode=5)
 WHERE 
    ([PL].ProductionDate >= { ts '2015-07-10 00:00:00' }   AND ([PL].ProductionDate <= { ts '2015-07-10 00:00:00' } OR [PL].ProductionDate Is Null)) 
AND ((1=1)  AND [ARC].CustomerKey IN (39) ) 
 GROUP BY 
     CASE WHEN [PC].[ProductCategoryCode] = 5870 THEN 'Trimmings' 
WHEN [PC].[ProductCategoryCode] = 5730 THEN 'Rib Tips'
WHEN [PC].[ProductCategoryCode] = 5990 THEN 'Skins'
ELSE [PC].[Description1] 
END
   , [ARC].CustomerKey
   , [PC].ProductCategoryCode
   , CASE WHEN [PC].[ProductCategoryCode] = 5870 THEN [ICP].[UnitCost] 
WHEN [PC].[ProductCategoryCode] = 5730 THEN [ICP].[UnitCost] - 0.25 
WHEN [PC].[ProductCategoryCode] = 5990 THEN [ICP].[UnitCost] * 0 
ELSE [ICP].[UnitCost]
END
   , [ICP].UnitCost
   , [PC].ProcessCode
 ORDER BY 
     @Credits - SUM(Sum([PL].[OriginalQuantity_Stk])) OVER () 
   , CASE WHEN [PC].[ProductCategoryCode] = 5870 THEN SUM(SUM([PL].[OriginalQuantity_Stk])) OVER (PARTITION BY [PC].[ProductCategoryCode]) 
WHEN [PC].[ProductCategoryCode] = 5730 THEN SUM(SUM([PL].[OriginalQuantity_Stk])) OVER (PARTITION BY [PC].[ProductCategoryCode])
WHEN [PC].[ProductCategoryCode] = 5990 THEN SUM(SUM([PL].[OriginalQuantity_Stk])) OVER (PARTITION BY [PC].[ProductCategoryCode])
ELSE SUM(SUM([PL].[OriginalQuantity_Stk])) OVER()
END

我正在使用 Microsoft SQL Sever 2005。

如果我没理解错的话,你想把case放在里面window函数:

SUM(SUM(PL.OriginalQuantity_Stk)) OVER
       (PARTITION BY (CASE WHEN PC.ProductCategoryCode IN (5870, 5730, 5990)
                           THEN PC.ProductCategoryCode
                      END)
       ) as [Total Weight]

你能通过使用 2 个查询来做到这一点吗:

SELECT P.[PseudoCode], SUM(P.[OriginalQuantity_Stk]) AS CalcWeight FROM (
    SELECT CASE
        WHEN [PC].[ProductCategoryCode] = 5730 THEN '5730'
        WHEN [PC].[ProductCategoryCode] = 5870 THEN '5870'
        WHEN [PC].[ProductCategoryCode] = 5990 THEN '5990'
            ELSE 'ELSE' END AS PseudoCode, [PL].[OriginalQuantity_Stk]
    FROM IC_Products [PC]) P
GROUP BY PseudoCode

此外,在您的查询中,您有太多的 case 语句...您是否考虑过设置一个 table 变量并将每个 ProductCategoryCode 的所有不同值放入其中,然后加入这个 table?代码将更易于阅读和维护。