Фильтр SELECT результатов по одному столбцу - PullRequest
0 голосов
/ 16 марта 2019

Я работаю с таблицей «Маршрут», в которой указан упорядоченный набор «Стадий» для определенного ProductID:

| ID | ProductID | StageID | Order |
|----+-----------+---------+-------|
|  0 |         1 |       4 |     1 |
|  1 |         1 |       2 |     2 |
|  2 |         1 |       3 |     3 |
|  3 |         1 |       7 |     4 |
|  4 |         1 |       5 |     5 |
|----+-----------+---------+-------|

И таблица «Записи», в которой указаны результаты PASS / FAIL с метками времени для серийного номера продукта на определенной стадии:

| ID | RecordDate          | Serial Number | StageID | Result |
|----+---------------------+---------------+---------+--------|
|  0 | 2019-03-16 00:00:00 | G001          |       4 |      1 |
|  1 | 2019-03-16 00:01:00 | G001          |       2 |      1 |
|  2 | 2019-03-16 00:02:00 | G001          |       2 |      0 |
|----+---------------------+---------------+---------+--------|

Из приведенных выше гипотетических данных видно, что серийный номер G001 прошел через стадию 4 и PASSED, затем стадию 2 и PASSED, но затем он снова прошел стадию 2 и завершился неудачей.

Теперь я хочу выбрать результаты из этой таблицы записей для определенного серийного номера, где в маршруте существует идентификатор продукта для этого продукта. Это просто - вот мой запрос:

SELECT StageID, Result, RecordDate
FROM Records
WHERE StageID IN (SELECT StageID FROM Route WHERE ProductID = 1) AND SerialNumber = 'G001';

Для приведенных выше данных это дает мне:

| StageID | Result | RecordDate          |
|---------+--------+---------------------|
|       4 |      1 | 2019-03-16 00:00:00 |
|       2 |      1 | 2019-03-16 00:00:01 |
|       2 |      0 | 2019-03-16 00:00:02 |
|---------+--------+---------------------|

Теперь сложный момент, когда мои знания о SQL, к сожалению, истекают, заключается в том, что я хочу фильтровать по StageID, чтобы отображался только самый недавний результат в таблице записей для этого StageID и SerialNumber. Итак, в данном примере я хочу это:

| StageID | Result | RecordDate          |
|---------+--------+---------------------|
|       4 |      1 | 2019-03-16 00:00:00 |
|       2 |      0 | 2019-03-16 00:00:02 |
|---------+--------+---------------------|

Фильтрация может быть выполнена по RecordDate или, еще проще, по Records.ID.

Но я не могу понять SQL, который бы достиг этого, и я думаю, что это тот случай, когда я недостаточно знаю язык, чтобы сформулировать то, что я пытаюсь сделать.

Итак, мой вопрос: возможно ли отфильтровать эти результаты по самой последней записи для каждого StageID?

Я играл с опциями GROUP BY безрезультатно.

Ответы [ 2 ]

1 голос
/ 16 марта 2019

Используйте функции окна:

SELECT r.StageID, r.Result, r.RecordDate
FROM (SELECT r.*
             ROW_NUMBER() OVER (PARTITION BY r.StageID ORDER BY r.RecordDate DESC) as seqnum
       FROM Records r
     ) JOIN
     Route ro
     ON ro.StageID = r.StageID AND ro.ProductId = 1
WHERE r.SerialNumber = 'G001';

Или, вы можете добавить

SELECT r.StageID, r.Result, r.RecordDate
FROM Records r
WHERE r.StageID IN (SELECT ro.StageID
                    FROM Route ro
                    WHERE ro.ProductID = 1
                   ) AND
      r.SerialNumber = 'G001' AND
      r.RecordDate = (SELECT MAX(r2.RecordDate)
                      FROM records r2
                      WHERE r2.StageId = r.StageId
                     );
0 голосов
/ 16 марта 2019
WITH cte 
     AS (SELECT StageID, 
                Result, 
                RecordDate, 
                Row_number() 
                  OVER( 
                    partition BY StageID 
                    ORDER BY Record_Date DESC) AS rn 
         FROM   table) 
SELECT StageID, 
       Result, 
       RecordDate 
FROM   cte 
WHERE  rn = 1 
ORDER  BY StageID DESC 
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...