SQL Server选择Distinct并使用CASE排序

时间:2015-02-26 00:26:10

标签: sql sql-order-by case distinct

我已经看过很多关于这种情况的问题/论坛帖子,但我要么不理解解决方案,要么提供的解决方案对于特定问题太具体了,我不知道如何把它应用到我的情况。我有以下查询:

SELECT DISTINCT d.*
FROM Data d
JOIN Customers c 
ON c.Customer_Name = d.Customer_Name
AND c.subMarket = d.subMarket
JOIN Sort s 
ON s.Market = c.Market
ORDER BY d.Customer_Name, d.Category, d.Tab, d.SubMarket,
CASE s.sortBy
WHEN 'Comp_Rank'
THEN d.Comp_Rank
WHEN 'Market_Rank'
THEN d.Market_Rank
ELSE d.Other_Rank
END

我在我的MySQL数据库上使用了那个确切的查询,它运行得很好。我们最近切换到SQL Server数据库,现在它没有工作,我得到错误:

ORDER BY items must appear in the select list if SELECT DISTINCT is specified.

我尝试将s。*添加到SELECT中(因为s.sortBy在CASE中)并且没有改变任何内容我也尝试列出数据中的每个字段在SELECT中排序并导致相同的确切错误。

数据中实际上没有重复,但是当我进行连接时,每个项目会产生4个完全重复的行,而我不知道如何解决这个问题,这就是为什么我最初添加了DISTINCT。我尝试过LEFT JOIN,INNER JOIN等的各种变换......并且无法获得不同的结果。无论如何,任何一个问题的解决方案都可以,但我假设需要更多信息来找出JOIN重复问题。

编辑:我刚刚意识到我错误地输入了ORDER BY中的一些字段(例如,n.Category,n.Tab应该是d.Category,d.Tab)。 ORDER BY中的所有内容都来自我选择的数据表*。正如我所说,我也尝试列出SELECT中的每个字段,但没有帮助。

3 个答案:

答案 0 :(得分:5)

如错误所示,当您使用select distinct时,您必须按select子句中的表达式排序。因此,您的case是一个问题,而且所有列都不是来自d

您可以使用group by来修复此问题,并包括您要排序的列。由于案例包含s中的列,因此您需要在case中添加group by(或至少包含该列):

SELECT d.*
FROM Data d JOIN
     Customers c 
     ON c.Customer_Name = d.Customer_Name AND
        c.subMarket = d.subMarket JOIN Sort s 
     ON s.Market = c.Market
GROUP BY "d.*",
         (CASE s.sortBy WHEN 'Comp_Rank' THEN d.Comp_Rank
                        WHEN 'Market_Rank' THEN d.Market_Rank
                        ELSE d.Other_Rank
         END)
ORDER BY d.Customer_Name, d.Category, d.Tab, d.SubMarket,
         (CASE s.sortBy WHEN 'Comp_Rank' THEN d.Comp_Rank
                        WHEN 'Market_Rank' THEN d.Market_Rank
                        ELSE d.Other_Rank
         END)

请注意,"d.*"在引号中。您需要列出group by

中的所有列

答案 1 :(得分:1)

试试这个:

SELECT DISTINCT d.Customer_Name, d.Category, d.Tab, d.SubMarket,
  CASE s.sortBy
    WHEN 'Comp_Rank'
      THEN d.Comp_Rank
    WHEN 'Market_Rank'
      THEN d.Market_Rank
    ELSE
      d.Other_Rank
  END

FROM Data d

JOIN Customers c 
  ON c.Customer_Name = d.Customer_Name
 AND c.subMarket = d.subMarket

JOIN Sort s 
  ON s.Market = c.Market

ORDER BY d.Customer_Name, d.Category, d.Tab, d.SubMarket,
  CASE s.sortBy
    WHEN 'Comp_Rank'
      THEN d.Comp_Rank
    WHEN 'Market_Rank'
      THEN d.Market_Rank
    ELSE
      d.Other_Rank
  END

答案 2 :(得分:0)

为了跟进这一点,您只需要将案例添加到带有 AS 的 SELECT 中。然后将该引用包含在 ORDER BY 列表中。

SELECT DISTINCT d.*, case when ... then ... else ... end AS MyCase
...
ORDER BY d.Customer_Name, d.Category, d.Tab, d.SubMarket, MyCase

这个答案与 Pang 的相似,但我发现不必在顶部和底部都包含 case 语句更好,因为如果您修改一个而不是另一个,则可能会出现错误。