sql server 查询 order by 与 union 并替换多个列的空值
Posted
技术标签:
【中文标题】sql server 查询 order by 与 union 并替换多个列的空值【英文标题】:sql server query order by with union and replacing multiple columns' null value 【发布时间】:2012-09-28 09:21:41 【问题描述】:我有一个查询要从 4 个不同的表中获取记录。我正在使用union
来获取最终记录。我的问题是我在所有 4 个表中没有相同数量和类型的列,所以我正在制作具有 null
值的虚拟列。我面临的问题是排序。我正在使用 datetime desc 对记录进行排序,但有时当日期相同时,我希望警报上的二级排序列可以是 High、Medium 或 Null 类型。我想要 Null 列在底部,但我在顶部。所以我尝试在ORDER BY
子句中使用ISNULL(column_name, 'aaaa')
,但我没有得到实际结果。任何人都可以帮忙吗?
SELECT CreatedDt as 'Date/Time' , null AS [Alert_Type] FROM TblA
union
SELECT CreatedDt as 'Date/Time' , null AS [Alert_Type] FROM TblB
union
SELECT CreatedDt as 'Date/Time' , null AS [Alert_Type] FROM TblC
union
SELECT CreatedDt as 'Date/Time' , Alert_Type FROM TblD
ORDER BY CreatedDt, ISNULL (Alert_Type,'aa') DESC
错误是
ORDER BY items must appear in the select list if the statement contains a UNION, INTERSECT or EXCEPT operator.
谢谢你..
【问题讨论】:
你能分享一下查询吗? @Vikdor 和 NG - 我已经发布了 嗯。您需要 SQL Server 和 Oracle 的解决方案吗? (plsql
是 Oracle 的 SQL 方言)
【参考方案1】:
试试这个:
select * from (
SELECT CreatedDt as 'Date/Time' , null AS [Alert_Type] FROM TblA
union
SELECT CreatedDt as 'Date/Time' , null AS [Alert_Type] FROM TblB
union
SELECT CreatedDt as 'Date/Time' , null AS [Alert_Type] FROM TblC
union
SELECT CreatedDt as 'Date/Time' , Alert_Type FROM TblD)a
order by CreatedDt desc,
case when Alert_Type is null then 0 else 1 end
【讨论】:
谢谢。但是 TblA、TblB 和 TblC 中不存在 Alert_Type 列,因此对于联合子句,我在选择查询中创建了具有空值的虚拟列 [Alert_Type]。您的解决方案给了我同样的错误“如果语句包含 UNION、INTERSECT 或 EXCEPT 运算符,则选择列表中必须出现无效的列名 'Alert_Type'.ORDER BY 项。” @DevendraGohil:这不可能发生,您是否复制了我的完整查询并执行了它。查看此链接以获取示例sqlfiddle.com/#!2/d41d8/2410 @DevendraGohil - 请发布您修改后的查询。这种方法应该可以正常工作。我认为您可能在最终实现它时遗漏了一些东西。 @MartinSmith 在order by
中,union
查询之后似乎不允许表达式引用列。我无法在文档中确认这一点。
@NikolaMarkovinović - 如果联合在派生表中(如此处)并且按外部排序,则很好。【参考方案2】:
如果Alert_Type
在TblD
中不能为NULL,您可以这样做:
SELECT CreatedDt as 'Date/Time' , 'aa' AS [Alert_Type] FROM TblA
union
SELECT CreatedDt as 'Date/Time' , 'aa' AS [Alert_Type] FROM TblB
union
SELECT CreatedDt as 'Date/Time' , 'aa' AS [Alert_Type] FROM TblC
union
SELECT CreatedDt as 'Date/Time' , Alert_Type FROM TblD
ORDER BY CreatedDt DESC, Alert_Type DESC
注意CreatedDt
之后的DESC
(因为你说你想按日期时间列降序排序)。
【讨论】:
我试过了,但在这种情况下它不起作用,因为它没有优先按 CreatedDt 按 desc 顺序排序。我想主要按 CreatedDt 排序,如果多个记录的 CreatedDt 相同,而不是仅按 Alert_Type desc 排序 @DevendraGohil 此查询生成的行的顺序与您的相同。如果要对 CreatedDt 进行降序排序,请在ORDER BY CreatedDt
之后插入 desc
。
@DevendraGohil:我更新了我的答案,以展示如何为主要排序标准指定降序。 (在您的帖子中错过了那一点,抱歉。)【参考方案3】:
您仍然可以在 ORDER BY
子句中使用 CASE
ORDER BY CASE WHEN column_name IS NULL
THEN 1
ELSE 0
END ASC --, other sorts
-- in these case NULL columns should be on the bottom part
【讨论】:
谢谢,我试过 SELECT CreatedDt as 'Date/Time' , null AS [Alert_Type] FROM TblA union SELECT CreatedDt as 'Date/Time' , null AS [Alert_Type] FROM TblB union SELECT CreatedDt as 'Date/Time' , null AS [Alert_Type] FROM TblC union SELECT CreatedDt as 'Date/Time' , Alert_Type FROM TblD ORDER BY CreatedDt, column_name IS NULL THEN 1 END DESC 但出现错误“ORDER BY 项目必须出现在选择中列出语句是否包含 UNION、INTERSECT 或 EXCEPT 运算符。"以上是关于sql server 查询 order by 与 union 并替换多个列的空值的主要内容,如果未能解决你的问题,请参考以下文章
SQL Server查询错误-ORDER BY子句在视图中无效
SQL Server 查询错误 -ORDER BY 子句在视图中无效
在SQL Server的子查询视图内联函数等数据库对象中,不应该单独使用ORDER BY语句
JPA 和 SQL Server 的 ORDER BY 子句中的列无效