ali khanna Ответов: 2

Как получить текущее и следующее значение строки в одной строке с помощью MSSQL


Я новичок в SQL и застрял в проблеме, когда мне приходится извлекать значения следующим образом:
существующий объект DataTable
ID | Date
01 | 3/3/17
02 | 4/3/17
03 | 8/3/17
04 | 1/4/17


Я хочу, чтобы данные были выбраны следующим образом:

ID  | Date1  | Date2
01  | 3/3/17 | 4/3/17 
02  | 4/3/17 | 8/3/17
03  | 8/3/17 | 1/4/17
04  | 1/4/17 | null


Пожалуйста, направьте мне SQL-запрос, чтобы выбрать вышеуказанный способ.

Что я уже пробовал:

по какой-то ссылке я попробовал:

SELECT A.Id , 
               A.Date AS CurDate , 
               B.Date AS NxtDate 
FROM words AS A
LEFT JOIN words AS B ON A.Date < B.Date 


(ID будет GUID, поэтому я не рассматриваю Id ни в каком состоянии)
Это не дает ожидаемого результата..

kmoorevs

Это последняя дата верна? (или это должен быть 2018 год) если даты должны быть упорядочены по возрастанию, вы можете использовать подзапросы, чтобы делать то, что вы хотите. Если это так, я могу привести пример, который работает.

2 Ответов

Рейтинг:
2

MadMyche

Это работает с вашими текущими данными; однако вы сами по себе, если переключитесь на GUID

DECLARE @Table TABLE (ID INT IDENTITY(1,1) NOT NULL, TheDate DATE)

INSERT @Table(TheDate) 
values ('03/03/2017'), ('04/03/2017'), ('08/03/2017'), ('01/04/2017')

SELECT a.ID
     , Date1 = a.TheDate
     , Date2 = b.TheDate

FROM            @Table  a
LEFT OUTER JOIN @Table  b ON a.ID + 1 = b.ID

ORDER BY A.ID


Рейтинг:
14

CHill60

Глядя на ваши ожидаемые данные, кажется, что они находятся в порядке дат. Вы можете назначить номер строки на этой основе, который заменяет идентификатор, используемый в решении 1 (и поэтому будет работать с GUID в качестве идентификатора), например

DECLARE @Table TABLE (ID INT IDENTITY(1,1) NOT NULL, TheDate DATE)

INSERT @Table(TheDate) 
values ('03-MAR-2017'), ('04-MAR-2017'), ('08-MAR-2017'), ('01-APR-2017')
;WITH CTE AS
(
    SELECT ID, TheDate
    ,ROW_NUMBER() OVER(ORDER BY TheDate) AS rn
    FROM @Table
)
SELECT CTE.ID, CTE.TheDate As Date1, NXT.TheDate As Date2
FROM CTE
LEFT OUTER JOIN CTE NXT ON NXT.rn = CTE.rn + 1
Если у вас есть SQL Server 2012 (не экспресс-версия) или более поздняя версия (включая 2014 Express), то вместо этого вы можете использовать оконные функции (гораздо аккуратнее)
SELECT ID, TheDate, LEAD(TheDate,1) OVER (ORDER BY TheDate) FROM @Table


ali khanna

Спасибо

Richard Deeming

"SQL Server 2012 (не экспресс-версия)"

LEAD и LAG отлично работает в SQL 2012 Express.

CHill60

Отличные новости, ваше здоровье. Прошло уже некоторое время с тех пор, как я смотрел, но я был уверен, что эта цитата была из документации M$ - в то время я не был в состоянии доказать это в любом случае. Думаю, мне лучше обновить свою статью, которая цитирует его! (на определенном этапе)