ROW_NUMBER () SQL 2005 Query возвращает Null - PullRequest
0 голосов
/ 16 февраля 2011

У меня возникли проблемы при сравнении данных из двух разных периодов таблицы с использованием ROW_NUMBER() в SQL Server 2005 из-за пустых значений.

Я был бы рад, если кто-нибудь может мне помочь.

CREATE TABLE MOV (ID INT,DATE_TIMEID DATETIME,AMOUNT MONEY)

INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1367, '2011-01-04 00:00:00',    1238.75)    
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1367, '2010-01-05 00:00:00',    1220.75)
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1367, '2011-01-05 00:00:00',    1000.50)    
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1367, '2010-01-06 00:00:00',    1111.25)
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1367, '2011-01-06 00:00:00',    1065.25)    
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1367, '2010-01-07 00:00:00',    939.75)
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1367, '2011-01-07 00:00:00',    1606.25)    
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1367, '2010-01-08 00:00:00',    1364.25)
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1367, '2011-01-08 00:00:00',    2379.75)
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1367, '2010-01-09 00:00:00',    908.25)
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1367, '2011-01-09 00:00:00',    35.25)
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1367, '2010-01-10 00:00:00',    1.50)
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1368, '2010-01-04 00:00:00',    1164.80)    
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1368, '2010-01-05 00:00:00',    1385.50)    
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1368, '2010-01-06 00:00:00',    1683.90)    
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1368, '2010-01-07 00:00:00',    1420.80)    
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1368, '2010-01-08 00:00:00',    173.70) 
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1368, '2010-01-09 00:00:00',    117.50)
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1368, '2010-01-10 00:00:00',    1052.20)    
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1404, '2011-01-03 00:00:00',    1052.20)    
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1404, '2011-01-04 00:00:00',    1164.80)    
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1404, '2011-01-05 00:00:00',    1385.50)    
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1404, '2011-01-06 00:00:00',    1683.90)
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1404, '2011-01-07 00:00:00',    1420.80)    
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1404, '2011-01-08 00:00:00',    173.70) 
INSERT INTO MOV (ID,DATE_TIMEID,AMOUNT)VALUES(1404, '2011-01-09 00:00:00',    117.50) 

Вот запрос:

SELECT MOV1.ROWID,
       MOV1.ID,
       MOV1.DATE_TIMEID,
       MOV1.AMOUNT,
       MOV2.ROWID                    ROWID2,
       MOV2.ID                       ID2,
       MOV2.DATE_TIMEID              Date_timeID2,
       MOV2.AMOUNT                   Amount2,
       ( MOV1.AMOUNT - MOV2.AMOUNT ) Diff,
       CASE
         WHEN MOV1.AMOUNT = 0 THEN 0
         ELSE ( ( ( MOV1.AMOUNT - MOV2.AMOUNT ) * 100 ) / MOV1.AMOUNT )
       END                           AmountToPercent
from   (select ROW_NUMBER() OVER (ORDER BY CASE WHEN MOV.ID IS NULL THEN 0 ELSE
               MOV.ID
                      END,
               CASE WHEN MOV.DATE_TIMEID IS NULL THEN '01/01/1900' ELSE
               MOV.DATE_TIMEID
                      END ASC
               )
               AS
                      'ROWID',
               CAST(MOV.ID as CHAR(4)) /*+ ' - ' + V_ParkingUserAccess.ParkingName*/
               ID,
               DATE_TIMEID,
               Sum(AMOUNT)
               AMOUNT
        from   dbo.MOV
        where  MOV.ID between 1367 and 1404
               and DATE_TIMEID >= '01/03/2011'
               and DATE_TIMEID <= '01/09/2011'
        group  by MOV.ID,
                  DATE_TIMEID) MOV1
       INNER JOIN (select ROW_NUMBER() OVER (ORDER BY MOV.ID, MOV.DATE_TIMEID
                          ASC) AS
                          'ROWID',
                          MOV.ID
                          ID,
                          DATE_TIMEID
                                                       DATE_TIMEID,
                          Sum(AMOUNT)
                                                       AMOUNT
                   from   dbo.MOV
                   where  MOV.ID between 1367 and 1404
                          and DATE_TIMEID >= '01/04/2010'
                          and DATE_TIMEID <= '01/10/2010'
                   group  by MOV.ID,
                             DATE_TIMEID) MOV2
         ON MOV1.ROWID = MOV2.ROWID
            and MOV1.ID = MOV2.ID  

1 Ответ

1 голос
/ 17 февраля 2011

Наконец-то увидел.

Строки для ID = 1367 содержат значения даты из обоих диапазонов дат 01/03/2011..01/09/2011 и 01/04/2010..01/10/2010. И поэтому они выбираются с обеих сторон внутреннего соединения, и соединение происходит соответственно.

Два других имеют либо один диапазон дат, либо другой. Следовательно, один из подвыборов не возвращает строк. И поскольку это ВНУТРЕННЕЕ объединение, в конечном итоге вы не получите строк для этих идентификаторов.

...