2017-06-07 1 views
0

Ich habe ein Problem mit SQL. Ich fand eine ähnliche TOPIC, aber nicht genau das gleiche. Ich möchte die Daten, die sich überschneiden, trennen. Zum Beispiel habe ich in der ersten Reihe START_DATE 2014-08-06 und END_DATE 2014-10-06. Wir können sehen, dass die Daten aus der zweiten und der dritten Reihe innerhalb dieses Zeitraums ab der ersten Reihe liegen, aber ich muss es separat unter STORE_ID und INDEX_ID machen. Der Preis sollte aus der inneren Periode genommen werden. Ich kann diesen Code nicht ändern. Kannst du mir helfen?Teilen Sie Zeilen nach Datum und nach Gruppe SQL

Meine Tabelle sieht wie folgt aus:

declare @t table (STORE_ID INT, 
        INDEX_ID INT, 
        START_DATE datetime, 
        END_DATE datetime, 
        GROSS_SALES_PRICE decimal(10,2) 
      ); 

insert into @t 
values (1,20,'2014-08-06 00:00:00.000', '2014-10-06 23:59:59.000', 29.99), 
(1,20,'2014-09-06 00:00:00.000', '2014-09-09 23:59:59.000', 32.99), 
(1,20,'2014-09-10 00:00:00.000', '2014-09-30 23:59:59.000', 32.99), 
(1,20,'2014-10-07 00:00:00.000', '2049-12-31 23:59:59.000', 34.99), 
(1,22,'2014-08-06 00:00:00.000', '2014-10-06 23:59:59.000', 29.99), 
(1,22,'2014-09-06 00:00:00.000', '2014-09-09 23:59:59.000', 32.99), 
(1,22,'2014-09-10 00:00:00.000', '2014-09-30 23:59:59.000', 32.99), 
(1,22,'2014-10-07 00:00:00.000', '2049-12-31 23:59:59.000', 34.99), 
(2,20,'2014-08-06 00:00:00.000', '2014-10-06 23:59:59.000', 29.99), 
(2,20,'2014-09-06 00:00:00.000', '2014-09-09 23:59:59.000', 32.99), 
(2,20,'2014-09-10 00:00:00.000', '2014-09-30 23:59:59.000', 32.99), 
(2,20,'2014-10-07 00:00:00.000', '2049-12-31 23:59:59.000', 34.99) 

und die gewünschte Ausgabe:

declare @t2 table (STORE_ID INT, 
        INDEX_ID INT, 
        START_DATE datetime, 
        END_DATE datetime, 
        GROSS_SALES_PRICE decimal(10,2) 
        ); 

insert into @t2 
values (1,20,'2014-08-06 00:00:00.000', '2014-09-05 23:59:59.000', 29.99), 
    (1,20,'2014-09-06 00:00:00.000', '2014-09-09 23:59:59.000', 32.99), 
    (1,20,'2014-09-10 00:00:00.000', '2014-09-30 23:59:59.000', 32.99), 
    (1,20,'2014-10-01 00:00:00.000', '2014-10-06 23:59:59.000', 29.99), 
    (1,20,'2014-10-07 00:00:00.000', '2049-12-31 23:59:59.000', 34.99), 
    (1,22,'2014-08-06 00:00:00.000', '2014-09-05 23:59:59.000', 29.99), 
    (1,22,'2014-09-06 00:00:00.000', '2014-09-09 23:59:59.000', 32.99), 
    (1,22,'2014-09-10 00:00:00.000', '2014-09-30 23:59:59.000', 32.99), 
    (1,22,'2014-10-01 00:00:00.000', '2014-10-06 23:59:59.000', 29.99), 
    (1,22,'2014-10-07 00:00:00.000', '2049-12-31 23:59:59.000', 34.99), 
    (2,20,'2014-08-06 00:00:00.000', '2014-09-05 23:59:59.000', 29.99), 
    (2,20,'2014-09-06 00:00:00.000', '2014-09-09 23:59:59.000', 32.99), 
    (2,20,'2014-09-10 00:00:00.000', '2014-09-30 23:59:59.000', 32.99), 
    (2,20,'2014-10-01 00:00:00.000', '2014-10-06 23:59:59.000', 29.99), 
    (2,20,'2014-10-07 00:00:00.000', '2049-12-31 23:59:59.000', 34.99) 

So sollte der Code wie in dem Thema arbeite ich angebracht, aber es sollte es auf jeden separat tun STORE_ID und INDEX_ID.

+2

'selbige denken wie in diesem Thema' ... nein, Ihre Frage muss auf eigenen Füßen stehen. Bitte bearbeiten Sie Ihre Frage und geben Sie eine klare Problemstellung ab. –

+0

fertig, ich denke es ist jetzt klar. Entschuldigung – Masher

+0

Zeigen Sie Ihre erwartete OutPut –

Antwort

1
;WITH Preprocessed AS (
    SELECT STORE_ID, INDEX_ID, START_DATE, END_DATE, 
     NEXT_START_DATE = FIRST_VALUE(START_DATE) OVER (PARTITION BY STORE_ID, INDEX_ID ORDER BY START_DATE ROWS BETWEEN 1 FOLLOWING AND 1 FOLLOWING), 
     MAX_END_DATE = MAX(END_DATE) OVER(PARTITION BY STORE_ID, INDEX_ID ORDER BY START_DATE ROWS UNBOUNDED PRECEDING) 
    FROM @t 
) 
SELECT 
    STORE_ID, INDEX_ID, START_DATE, 
    END_DATE_NEW = IIF(NEXT_START_DATE IS NOT NULL AND NEXT_START_DATE < END_DATE, DATEADD(SECOND, -1, NEXT_START_DATE), END_DATE) 
FROM Preprocessed 

UNION ALL 

SELECT STORE_ID, INDEX_ID, 
    START_DATE = DATEADD(SECOND, 1, END_DATE), 
    END_DATE = IIF(NEXT_START_DATE < MAX_END_DATE, DATEADD(SECOND, -1, NEXT_START_DATE), MAX_END_DATE) 
FROM Preprocessed 
WHERE (NEXT_START_DATE IS NULL OR NEXT_START_DATE > DATEADD(SECOND, 1, END_DATE)) -- End of the range 
    AND (END_DATE < MAX_END_DATE)             -- Check if need to add new record after range 
ORDER BY 1, 2, 3