3

SQL Server2008R2を使用しています。私は次のデータを持っています:

ID   Value   OrderNumber
1      A         NULL
2      E          4
3      C         NULL
4      B         NULL
5      F          2
6      D         NULL

OrderNumber値を考慮してOrderNumber列によるデータの順序をフェッチする必要があるクエリを作成したいと思います。クエリ結果は次のとおりである必要があります。

ID      Value     OrderNumber
1         A           NULL
5         F            2  --indicates row must be second in result set. 
3         C           NULL
2         E            4  --indicates row must be fourth in result set.
4         B           NULL
6         D           NULL

読んでくれてありがとう、そしてあなたの答え。

4

3 に答える 3

3

さまざまな方法を試しましたが、必要な結果が保証された方法で得られる唯一の方法は次のとおりです。

declare @t table (ID int not null,Value char(1) not null,OrderNumber int null)
insert into @T(ID,Value,OrderNumber) values
(1,'A',NULL),
(2,'E',4),
(3,'C',NULL),
(4,'B',NULL),
(5,'F',2),
(6,'D',NULL)

;With Nbrs as (
    select ROW_NUMBER() OVER (ORDER BY ID) as n from @t
), AvailableNbrs as (
    select n,ROW_NUMBER() OVER (ORDER BY n) as rn from Nbrs where n not in (select OrderNumber from @t where OrderNumber is not null)
), RequiredOrders as (
    select ID,ROW_NUMBER() OVER (ORDER BY ID) as rn from @t where OrderNumber is null
)
select
    *,COALESCE(OrderNumber,an.n) as FinalOrder
from
    @t t
        left join
    RequiredOrders ro
        on
            t.ID = ro.ID
        left join
    AvailableNbrs an
        on
            ro.rn = an.rn
order by COALESCE(OrderNumber,an.n)

いくつかの CTE を使用して、OrderNumber現在割り当てられていない を見つけ、それらの 1-1 を を持たない行と照合しますOrderNumber

結果:

|--------- @t --------------| |----- RequiredOrders ---------| |----- AvailableNbrs -------------------| |- COALESCE -------|
ID          Value OrderNumber ID          rn                   n                    rn                   FinalOrder
----------- ----- ----------- ----------- -------------------- -------------------- -------------------- --------------------
1           A     NULL        1           1                    1                    1                    1
5           F     2           NULL        NULL                 NULL                 NULL                 2
3           C     NULL        3           2                    3                    2                    3
2           E     4           NULL        NULL                 NULL                 NULL                 4
4           B     NULL        4           3                    5                    3                    5
6           D     NULL        6           4                    6                    4                    6
于 2012-10-29T14:40:22.813 に答える
1

受け入れられた答えよりもはるかに優れた解決策を見つけました:

declare @t table(id int, value char, ordernumber int)

insert @t values(1,'A', null)
insert @t values(2,'E',4)
insert @t values(3,'C',NULL)
insert @t values(4,'B',NULL)
insert @t values(5,'F',2)
insert @t values(6,'D',NULL)

;with a as
(
select *, row_number() over (order by id)+.1 rn1 from @t
where ordernumber is null
union all
select *, ordernumber - rank() over (order by ordernumber)+1 rn1 from @t
where ordernumber is not null
)
select * from a order by rn1, ordernumber
于 2012-10-29T15:03:47.610 に答える
0

これを試して:

SELECT   *
FROM     tableName
Order BY  CASE WHEN OrderNumber IS NULL THEN ID ELSE OrderNumber END  
于 2012-10-29T14:19:11.920 に答える