SQL Запрос на получение 2-го из последних результатов с несколькими столбцами - PullRequest
1 голос
/ 29 мая 2020

Я пытаюсь получить 2-й самый последний результат для всех отдельных part_id (на основе order_date) до go в отчете, над которым я работаю, чтобы сравнить его с самыми последними результатами.

Прокомментированные разделы взяты из другого подхода, который я пытался, но безуспешно.

Любая помощь приветствуется!

(Боковое примечание: я новичок в публикации на SO, и заранее прошу прощения, если на это ответят в другом месте, но я не смог найти ничего, что относилось к этой проблеме)

Я использую следующий запрос:

SELECT
                              PURCHASE_ORDER.ORDER_DATE
                            , PURC_ORDER_LINE.PART_ID
                            , PURCHASE_ORDER.VENDOR_ID
                            , PURC_ORDER_LINE.LINE_STATUS
                            , PURC_ORDER_LINE.ORDER_QTY
                            , PURC_ORDER_LINE.UNIT_PRICE
                            --, ROW_NUMBER() over (ORDER BY PURCHASE_ORDER.ORDER_DATE DESC)AS ROW
                            , CAST (PURC_ORDER_LINE.ORDER_QTY * PURC_ORDER_LINE.UNIT_PRICE AS VARCHAR) AS TOTAL_COST
                    FROM
                              PURCHASE_ORDER
                              INNER JOIN
                                        PURC_ORDER_LINE
                              ON
                                        PURCHASE_ORDER.ID = PURC_ORDER_LINE.PURC_ORDER_ID

                    WHERE PURCHASE_ORDER.ORDER_DATE < (SELECT MAX(ORDER_DATE) FROM PURCHASE_ORDER) AND PURC_ORDER_LINE.PART_ID = 'XXXX'
                    ORDER BY ORDER_dATE DESC





                    --WHERE PURC_ORDER_LINE.PART_ID = 'XXXX' and PURCHASE_ORDER.ORDER_DATE = (SELECT MAX(ORDER_DATE) FROM PURCHASE_ORDER WHERE ORDER_DATE < (SELECT MAX(ORDER_DATE) FROM PURCHASE_ORDER))

EDIT 5/28 ПОЗДНЯЯ НОЧЬ:

Допустим, ниже приведен набор данных, который мне нужен второй результат для каждого part_id (второй основан на ORDER_DATE DES C)

+-------------+---------+-----------+
| ORDER_DATE  | PART_ID | VENDOR_ID |
+-------------+---------+-----------+
| 2020-05-29  | XXXX    | CVVB      |
| 2020-05-27  | XXXX    | CVVB      |
| 2020-05-28  | XXXX    | CVVA      |
| 2020-05-28  | YYYY    | GGNB      |
| 2020-04-12  | YYYY    | GGNB      |
| 2020-02-08  | YYYY    | GGNB      |
| 2020-05-28  | ZZZZ    | LLNB      |
| 2019-10-28  | ZZZZ    | LLNB      |
| 2019-05-27  | ZZZZ    | OKIJ      |
+-------------+---------+-----------+

Я хочу получить следующий результат (для более чем трех разных идентификаторов частей):

+------------+---------+-----------+
| ORDER_DATE | PART_ID | VENDOR_ID |
+------------+---------+-----------+
| 2020-05-28 | XXXX    | CVVA      |
| 2020-04-12 | YYYY    | GGNB      |
| 2019-10-28 | ZZZZ    | LLNB      |
+------------+---------+-----------+

В запросе также есть дополнительные столбцы, но их форматирование в виде таблицы заняло бы гораздо больше времени. Я оставил несколько столбцов в примерах.

ДРУГОЕ ИЗМЕНЕНИЕ

Я не уверен, помогает ли эта информация, но я Я пытаюсь сравнить самые последние результаты с предыдущими, чтобы показать различия в ценах и поставщиках. Мы компилируем данные в Report Builder; Мой подход заключался в том, чтобы создать 2 отдельных набора данных, один из которых был самым последним, а другой - вторым, и объединить данные из наборов данных в построителе отчетов. Если есть более простой подход и я иду в неправильном направлении, дайте мне знать!

Пример:

+------------+---------+-----------+-------------+----------+------------+
| ORDER_DATE | PART_ID | VENDOR_ID | Porder_Date | Ppart_ID | pVendor_id |
+------------+---------+-----------+-------------+----------+------------+
| 2020-05-29 | XXXX    | CVVB      | 2020-05-28  | XXXX     | CVVA       |
| 2020-05-28 | YYYY    | GGNB      | 2020-04-12  | YYYY     | GGNB       |
| 2020-05-28 | ZZZZ    | LLNB      | 2019-10-28  | ZZZZ     | LLNB       |
+------------+---------+-----------+-------------+----------+------------+

ИЗМЕНИТЬ НА СЛЕДУЮЩЕЕ УТРО

Спасибо всем за помощь! После того, как Гарри опубликовал свое решение, я пошел дальше и внес небольшие изменения, чтобы добавить нужные мне столбцы. Я заменил его часть объединения на исходный оператор выбора. Кажется, здесь все именно то, что я ищу!

Код:

;
WITH mycte AS
          (
                    SELECT
                              PURCHASE_ORDER.ORDER_DATE
                            , PURC_ORDER_LINE.PART_ID
                            , PURCHASE_ORDER.VENDOR_ID
                            , PURC_ORDER_LINE.LINE_STATUS
                            , PURC_ORDER_LINE.ORDER_QTY
                            , PURC_ORDER_LINE.UNIT_PRICE
                            , CAST (PURC_ORDER_LINE.ORDER_QTY * PURC_ORDER_LINE.UNIT_PRICE AS VARCHAR) AS TOTAL_COST
                    FROM
                              PURCHASE_ORDER
                              INNER JOIN
                                        PURC_ORDER_LINE
                              ON
                                        PURCHASE_ORDER.ID = PURC_ORDER_LINE.PURC_ORDER_ID
          )
        , mycte2 AS
          (
                    SELECT
                              CONVERT(DATE,order_date) AS order_date
                            , part_id
                            , vendor_id
                            , order_qty
                            , unit_price
                            , total_cost
                            , ROW_NUMBER() over(
                                      PARTITION BY part_id
                                      ORDER BY
                                                CONVERT(DATE,order_date) DESC) AS row_num
                    FROM
                              mycte
          )
SELECT
          mycte2.order_date
        , mycte2.part_id
        , mycte2.vendor_id
        , mycte2.order_qty
        , mycte2.unit_price
        , mycte2.total_cost
        , previous.order_date porder_date
        , previous.part_id    ppart_id
        , previous.vendor_id  pvendor_id
        , previous.order_qty  poqrder_qty
        , previous.unit_price punit_price
        , previous.total_cost ptotal_cost
FROM
          mycte2
          LEFT JOIN
                    mycte2 previous
          ON
                    previous.row_num   = mycte2.row_num +1
                    AND mycte2.part_id = previous.part_id
WHERE
          mycte2.row_num = 1

Ответы [ 2 ]

0 голосов
/ 29 мая 2020

На основе предоставленных вами данных вы можете сделать это с помощью функции cte и номера строки.

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

См. Код ниже

;with mycte as (


select 
 '2020-05-29' as order_date  , 'XXXX'  as part_id   , 'CVVB' as vendor_id
 union all select
 '2020-05-27'  , 'XXXX'    , 'CVVB'  
  union all select
 '2020-05-28'  , 'XXXX'    , 'CVVA'      
  union all select
 '2020-05-28'  , 'YYYY'    , 'GGNB'     
  union all select
 '2020-04-12'  , 'YYYY'    , 'GGNB'      
  union all select
 '2020-02-08'  , 'YYYY'    , 'GGNB'     
  union all select
 '2020-05-28'  , 'ZZZZ'    , 'LLNB'      
  union all select
 '2019-10-28' , 'ZZZZ'    , 'LLNB'    
  union all select
 '2019-05-27'  , 'ZZZZ'    , 'OKIJ' 
 )
 , mycte2 as (
 Select 
  convert(date,order_date) as order_date
 ,part_id
 ,vendor_id
 ,ROW_NUMBER() over( partition by part_id order by convert(date,order_date) desc) as row_num
 from mycte
)

Select 
mycte2.order_date
,mycte2.part_id
,mycte2.vendor_id
,previous.order_date porder_date
,previous.part_id ppart_id
,previous.vendor_id pvendor_id
from  mycte2

 left join mycte2 previous
    on previous.row_num = mycte2.row_num +1
    and mycte2.part_id = previous.part_id

where mycte2.row_num = 1

результат

Result

0 голосов
/ 29 мая 2020

Думаю, что-то вроде этого сработает, чтобы получить второй самый последний заказ:

;WITH cteOrders AS (
 SELECT ROW_NUMBER() OVER (ORDER BY Order_Date DESC) AS row_num,
    PURCHASE_ORDER.ORDER_DATE
    , PURC_ORDER_LINE.PART_ID
    , PURCHASE_ORDER.VENDOR_ID
    , PURC_ORDER_LINE.LINE_STATUS
    , PURC_ORDER_LINE.ORDER_QTY
    , PURC_ORDER_LINE.UNIT_PRICE
 FROM PURCHASE_ORDER 
 INNER JOIN PURC_ORDER_LINE ON PURCHASE_ORDER.ID = PURC_ORDER_LINE.PURC_ORDER_ID
 WHERE PURCHASE_ORDER.ORDER_DATE < (SELECT MAX(ORDER_DATE) FROM PURCHASE_ORDER) AND PURC_ORDER_LINE.PART_ID = 'XXXX'
 )
 SELECT * FROM cteOrders WHERE row_num = 2
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...