从表

时间:2016-07-01 11:37:01

标签: sql sql-server

我有一个奇怪的要求,理想情况下应该在SQL中解决,而不是周围的应用程序。

无论有多少实际可用,我都需要准确选择5行。在实践中,可用的行数通常小于5,并且在极少数情况下,它将超过5." extra"行应在每列中都有null

该应用程序使用的技术不是Turing Complete。在app的代码中,这个要求比你想象的要难得多!为了描述它,该应用程序实际上是一个变换器:它接收一堆查询并吐出报告。所以请理解该应用程序不是用编程语言编写的#34;在传统意义上。

例如,如果我有一张桌子:

A | B
-----
1 | X
2 | Y
3 | Z

然后有效的结果是

A    | B
-----------
2    | Y
1    | X
3    | Z
null | null
null | null

我知道这是一个不寻常的要求。遗憾的是,由于使用了该技术,它无法在应用程序中得到解决。

理想情况下,这不应该要求更改数据库,但如果没有其他方式可以安排更改。

有什么建议吗?

5 个答案:

答案 0 :(得分:7)

您可以这样做:

select top 5 a, b
from (select a, b, 1 as priority from t union all
      select null, null, 2 cross join
             (values(1, 2, 3, 4, 5)) v(5)
     ) x
order by priority;

即创建虚拟行,附加它们,然后选择前五行。

我认为这项工作应该在应用程序中完成,但您可以在SQL中完成。

答案 1 :(得分:3)

Create Table #Test (A int, B int)
Insert #Test Values (1,1)
Insert #Test Values (2,1)
Insert #Test Values (3,1)

Select Top 5 * From
    (
    Select A, B From #Test
    Union All
    Select Null, Null
    Union All
    Select Null, Null
    Union All
    Select Null, Null
    Union All
    Select Null, Null
    Union All
    Select Null, Null
    ) A

答案 2 :(得分:1)

将此包装在存储过程中..

declare @rowcount int 
select top 5* from dbo.test
set @rowcount=@@rowcount

if @rowcount<5
Begin
select * from dbo.test  
union all
select null  from dbo.numbers where n<=5-@rowcount
End

答案 3 :(得分:1)

如果使用某种计数表(尽管数字本身并不重要,只有表中有足够的记录),您可以使用它来创建虚拟行。例如使用sys.columns:

select top 5 a,b from
(
    select a, b, 0 ord from yourTable
    union all 
    select null a,null b, 1 from sys.columns
) t
order by ord

计数器的优点是,如果将来需要其他行数,您只需要更改顶部x(如果计数表有足够的行)

答案 4 :(得分:0)

从表中获取这3条记录。 拿一个计数器变量。 然后从你的代码中添加NULL内容,直到你的计数器得到5。