MS SQL: как выбрать самую последнюю запись из таблицы поиска для каждой пары внешних ключей - PullRequest
0 голосов
/ 07 сентября 2018

У меня есть справочная таблица, которая состоит из двух внешних ключей, которые образуют уникальную пару. Эти уникальные пары повторяются в таблице несколько раз при каждой транзакции, при этом каждый раз записывается новая дата / время.

Мне нужно найти способ вернуть только «самую последнюю» запись для каждой пары внешнего ключа и иметь возможность применить к ней дополнительную фильтрацию с помощью оператора WHERE.

Вот пример таблицы:

PK     PartPK  LocationPK  TransactionDate          Bin
16473  1       1           2018-09-03 15:24:57.100  NULL
16472  1       1           2018-09-03 13:24:27.250  NULL
16471  1       1           2018-09-03 13:07:11.777  NULL
16470  1       1           2018-09-03 11:19:57.557  NULL
16469  1       2           2018-09-03 09:32:27.050  NULL
16468  2       1           2018-09-03 07:28:16.250  NULL
16467  2       1           2018-09-03 00:09:30.383  NULL
16466  2       1           2018-08-31 14:21:24.803  NULL
16465  2       1           2018-08-31 13:29:52.253  NULL
16463  3       1           2018-08-31 13:13:47.977  NULL

Правильный запрос должен дать следующий результат:

PK     PartPK  LocationPK  TransactionDate          Bin
16473  1       1           2018-09-03 15:24:57.100  NULL
16469  1       2           2018-09-03 09:32:27.050  NULL
16468  2       1           2018-09-03 07:28:16.250  NULL
16463  3       1           2018-08-31 13:13:47.977  NULL

Для каждой отдельной пары PartPK и LocationPK я просто хочу строку с наибольшим значением TransactionDate. Я также хотел бы иметь возможность опираться на это, добавив в запрос «WHERE Bin is null», чтобы еще больше ограничить результаты.

Как мне этого добиться?

Ответы [ 3 ]

0 голосов
/ 07 сентября 2018
SELECT Q2.* FROM (SELECT DISTINCT t.PartPK, t.LocationPK FROM Yourtab t) Q1
                CROSS APPLY 
                    (SELECT TOP 1 * FROM Yourtab t2 
                            WHERE t2.PartPK = Q1.PartPK AND t2.LocationPK = Q1.LocationPK 
                                ORDER BY TransactionDate DESC) Q2
0 голосов
/ 07 сентября 2018

Сначала мы должны просто получить самые последние PK каждого PartPK and LocationPK, затем мы можем использовать его как подзапрос для возврата полной записи этого PK, как указано ниже:

CREATE TABLE #test(PK INT, PartPK INT, LocationPK INT, TransactionDate DATETIME, Bin INT)
INSERT INTO #test VALUES
(16473,1,1,'2018-09-03 15:24:57.100',NULL),
(16472,1,1,'2018-09-03 13:24:27.250',NULL),
(16471,1,1,'2018-09-03 13:07:11.777',NULL),
(16470,1,1,'2018-09-03 11:19:57.557',NULL),
(16469,1,2,'2018-09-03 09:32:27.050',NULL),
(16468,2,1,'2018-09-03 07:28:16.250',NULL),
(16467,2,1,'2018-09-03 00:09:30.383',NULL),
(16466,2,1,'2018-08-31 14:21:24.803',NULL),
(16465,2,1,'2018-08-31 13:29:52.253',NULL),
(16463,3,1,'2018-08-31 13:13:47.977',NULL)

SELECT t.* 
FROM #test t
INNER JOIN (
            SELECT MAX(PK) AS PK --We can use `TransactionDate` as well
            FROM #test
            GROUP BY PartPK, LocationPK) t1 ON t.PK = t1.PK

OUTPUT

PK      PartPK  LocationPK  TransactionDate         Bin
16473   1       1           2018-09-03 15:24:57.100 NULL
16469   1       2           2018-09-03 09:32:27.050 NULL
16468   2       1           2018-09-03 07:28:16.250 NULL
16463   3       1           2018-08-31 13:13:47.977 NULL
0 голосов
/ 07 сентября 2018

Вы можете использовать row_number() функцию:

select t.*
from (select t.*, row_number() over (partition by PartPK, LocationPK order by PK desc) as seq -- you can also order by TransactionDate
      from table t
     ) t
where seq = 1;
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...