Sql server 在一列上选择Distinct,并在Select Distinct中消除空值?

Sql server 在一列上选择Distinct,并在Select Distinct中消除空值?,sql-server,tsql,Sql Server,Tsql,照此 我有 ID SKU PRODUCT ======================= 1 FOO-23 Orange 2 BAR-23 Orange 3 FOO-24 Apple 4 FOO-25 Orange 5 FOO-25 null 6 FOO-25 null 预期结果: 1 FOO-23 Orange 3 FOO-24 Apple 5 FOO-25 null 6

照此 我有

    ID  SKU PRODUCT
    =======================
    1   FOO-23  Orange
    2   BAR-23  Orange
    3   FOO-24  Apple
    4   FOO-25  Orange
    5   FOO-25  null
    6   FOO-25  null
预期结果:

1   FOO-23  Orange
3   FOO-24  Apple
5   FOO-25  null
6   FOO-25  null
这个问题不能让我达到目的。如何在一列上选择DISTINCT,并在
SELECT DISTINCT
中消除
null

SELECT  *
FROM    (SELECT ID, SKU, Product,
                ROW_NUMBER() OVER (PARTITION BY PRODUCT ORDER BY ID) AS RowNumber
         FROM   MyTable
         WHERE  SKU LIKE 'FOO%') AS a
WHERE   a.RowNumber = 1

也许有一种方法是将带TIES的
与有条件的
分区一起使用

示例

Declare @YourTable Table ([ID] int,[SKU] varchar(50),[PRODUCT] varchar(50))
Insert Into @YourTable Values 
 (1,'FOO-23','Orange')
,(2,'BAR-23','Orange')
,(3,'FOO-24','Apple')
,(4,'FOO-25','Orange')
,(5,'FOO-25',NULL)
,(6,'FOO-25',NULL)

Select top 1 with ties * 
 From @YourTable
 Where SKU Like 'FOO%'
 Order By Row_Number() over (Partition By IsNull(Product,NewID()) Order By ID)
返回

ID  SKU     PRODUCT
6   FOO-25  NULL
5   FOO-25  NULL
3   FOO-24  Apple
1   FOO-23  Orange

这里使用John Cappelletti的样本数据是另一种方法。您真正需要的只是将OR谓词添加到where子句中

Declare @YourTable Table ([ID] int,[SKU] varchar(50),[PRODUCT] varchar(50))
Insert Into @YourTable Values 
 (1,'FOO-23','Orange')
,(2,'BAR-23','Orange')
,(3,'FOO-24','Apple')
,(4,'FOO-25','Orange')
,(5,'FOO-25',NULL)
,(6,'FOO-25',NULL)

SELECT  *
FROM
(
    SELECT ID
        , SKU
        , Product
        , ROW_NUMBER() OVER (PARTITION BY PRODUCT ORDER BY ID) AS RowNumber
    FROM   @YourTable
    WHERE  SKU LIKE 'FOO%'
) AS a
WHERE  a.RowNumber = 1
    OR a.PRODUCT IS NULL --This was the only part you were missing

我将您的排号更改为密集排列:

Declare @YourTable Table ([ID] int,[SKU] varchar(50),[PRODUCT] varchar(50))
Insert Into @YourTable Values 
 (1,'FOO-23','Orange')
,(2,'BAR-23','Orange')
,(3,'FOO-24','Apple')
,(4,'FOO-25','Orange')
,(5,'FOO-25',NULL)
,(6,'FOO-25',NULL)

SELECT  *
FROM    (SELECT ID, SKU, Product,
                Dense_RANK() OVER (PARTITION BY SKU ORDER BY Product) AS RowNumber
         FROM   @YourTable
         WHERE  left(SKU,3) = 'FOO') AS a
WHERE   a.RowNumber = 1
结果:

ID  SKU Product RowNumber
1   FOO-23  Orange  1
3   FOO-24  Apple   1
5   FOO-25  NULL    1
6   FOO-25  NULL    1

您想要的输出和解释相互冲突。您声明要消除NULL,但输出中有FOO-25。我想说你所需要的只是一个OR谓词。其中a.RowNumber=1或a.PRODUCT为空。我需要不同的产品和具有空值的产品。您是否可以在我建议的黑暗中尝试拍摄?这似乎仍然是你想要的。我甚至从来没有考虑过添加OR+1。真的谢谢,我不想在resultWell中添加rownumber列。这并不难……不要使用select*。无论如何,您不应该使用select*。你应该总是只选择那些你需要的列。稠密的列基本上允许连接,给它们相同的权重,并保持数字顺序(1,1,2,3)。RANK也会像奥运会一样发挥作用(1,1,3)