为什么 row_number 不适用于相同记录的 Null 值?

问题描述 投票:0回答:2

我正在尝试为同一 ID 有多行的查询之一应用行号。

例如this is what I have as table

现在,当我使用此代码使用

row_number over partition
时:

ROW_NUMBER() OVER (PARTITION BY ID, Race, ethnicity, Awards 
                   ORDER BY EnthnictyID ASC)

我明白了:

This is what I am getting after applying ROW_NUM

有数百万条记录具有相同的问题。

简而言之,我想用 value 替换 Null 并且确认一件事,所有 ID 都有自己的 Race、Ethnicity 和 Awards,因此所有 ID 都应该在各自的列中具有价值。

任何帮助将不胜感激!

谢谢

但我想看这个

ROW_NUMBER

Final Result with Value in Ethnicity

我已经应用的解决方案。

  1. 使用
    MIN
    MAX
    GROUP BY
    但它确实对某些人有效,但对其他人无效。
  2. 通过仅调用
    ROW_NUMBER = 1
    ,它返回带有
    NULL
    的重复项和一个具有值的重复项。
sql-server tsql null partition row-number
2个回答
0
投票

您得到两个不同的行号,因为 NULL 不等于“白色”。事实上,NULL 不等于其他任何东西,甚至 NULL 也不等于,这就是为什么有

IS [NOT] NULL
结构的原因。因此,由于引擎将 White 和 NULL 视为两个不同的值,因此您在窗口函数中得到两个不同的分区。

如果您只是想在列为 NULL 时使用某种统一的默认值,您可以将该列包装在

ISNULL(..., <default_value>)
中,例如:

ROW_NUMBER() OVER(PARTITION BY ID, Race, ISNULL(Ethnicity, 'White'), Awards ORDER BY EnthnictyID ASC)

这将使任何为 NULL 的 Ethnicity 等于“White”。或者,如果缺少种族,您可能希望将其等同于种族:

ROW_NUMBER() OVER(PARTITION BY ID, Race, ISNULL(Ethnicity, Race), Awards ORDER BY EnthnictyID ASC)

这更动态,因为如果你有一行 Race = Black,Ethnicity = NULL,它将将该行划分到与 Race = Black,Ethnicity = Black 相同的分区,而不是 Race = Black,Ethnicity = White你会得到

ISNULL(Ethnicity, 'White')
.

中的默认常量

现在,如果您尝试识别每个 ID 的重复项,并找出哪些行中填充的列最多,然后去掉其余的,您可能想按 ID 进行分区,然后按许多非空列进行排序你有,这会略有不同:

SELECT *
     , ROW_NUMBER() OVER (PARTITION BY ID 
                          ORDER BY IIF(Race IS NOT NULL, 1, 0) 
                                 + IIF(Ethnicity IS NOT NULL, 1, 0)   
                                 + IIF(Awards IS NOT NULL, 1, 0)
                              DESC) AS rn

  FROM yourTable

正如我在这里所做的那样,您可以在

PARTITION BY
ORDER BY
子句中使用各种表达式,这里我基本上按非空字段的计数排序(每个非空值生成一个 1,空值生成一个0).


0
投票

非常感谢您的回复。

我按照你说的那样尝试了 order by 但抛出了相同的结果。

我想要的是;我想用不是来自 RACE 的同一列中的值替换空值。

例如在屏幕截图中,您可以看到种族下的下一个值(第二行)是白色,因此我想分组并用白色替换 NULL 值。这就是它将如何在列中给出所有值的单行。

希望你明白了!

谢谢

© www.soinside.com 2019 - 2024. All rights reserved.