【问题标题】:Using CASE in SELECT to filter out NULL records在 SELECT 中使用 CASE 过滤掉 NULL 记录
【发布时间】:2016-11-30 20:26:38
【问题描述】:

我需要过滤不同的连接以选择 10 个列表中的前 4 个,但是由于不一致,它们并非都从 1 开始,并且有些有间隙。

我有以下代码来填充列表中 4 个中的第一个

COALESCE (CASE 
WHEN 1 IS NOT NULL THEN 1 END,
WHEN 2 IS NOT NULL THEN 2 END,
WHEN 3 IS NOT NULL THEN 3 END,
WHEN 4 IS NOT NULL THEN 4 END,
WHEN 5 IS NOT NULL THEN 5 END,
WHEN 6 IS NOT NULL THEN 6 END
 ) AS COL1

这很好,问题是我什么时候去做第二列。它返回的值与我无法与之前的 COL1 比较的值相同,因为它是别名。

任何帮助都会很棒!

【问题讨论】:

  • 只使用将搜索量限制为每个连接的前 4 个的条件,这样不管它们是否以 1 开头。
  • 带有查询的样本数据,具有预期的结果。您也许可以使用像row_number over (partition by.... order by....) as RN 这样的窗口函数来生成行号,然后过滤where RN <=4...

标签: sql sql-server-2008 tsql sql-server-2008-r2


【解决方案1】:

在 SQL Server 中,case 语句几乎不可能做到这一点——它们会变得非常复杂。

相反,您可以将数据反透视成行,然后将数据重新聚合到单独的列中,同时过滤掉NULLs。这是一个使用outer apply的例子:

select . . ., x.*
from . . . outer apply -- all your joins go here
     (select max(case when seqnum = 1 then col end) as col_1,
             max(case when seqnum = 2 then col end) as col_2,
             max(case when seqnum = 3 then col end) as col_3,
             max(case when seqnum = 4 then col end) as col_4             
      from (select col, row_number() over (order by ordering) as seqnum
            from (values (t1.col, 1), (t2.col, 2), . . . 
                 ) v(col, ordering)
            where col is not null
           ) v
     ) x

【讨论】:

    猜你喜欢
    • 2012-09-09
    • 1970-01-01
    • 1970-01-01
    • 2013-08-25
    • 1970-01-01
    • 1970-01-01
    • 2016-12-15
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多