从上个月的价格变动表中获取最后2个更新的unit_price

时间:2018-08-14 04:45:18

标签: mysql sql query-optimization

我有一个表格,记录每个成本价格,单位价格和特殊价格上商品的所有价格变化。即使其中一种定价已从旧定价更改为零,该表也会记录数据。表结构示例如下。

 id | item_id | cost_price  | unit_price   | special_price | created_date
---------------------------------------------------------------------------
  1 |   101   |    100      |  NULL        |   NULL        | 2018-07-15 10:02:20
  2 |   102   |   NULL      |  250         |   NULL        | 2018-07-16 12:23:00
  3 |   101   |   NULL      |  150         |   NULL        | 2018-07-16 10:02:20
  4 |   101   |   NULL      |  200         |   NULL        | 2018-07-18 12:23:00
  5 |   101   |   NULL      |  201         |   NULL        | 2018-07-22 10:02:20
  6 |   102   |   NULL      |  283         |   NULL        | 2018-07-28 12:23:00

我想从上表(日期为2018年7月13日)获得上个月的以下输出

item_id   |   unit_price   | changed_date
-----------------------------------------
   101    |    201         | 2018-07-22 10:02:20
   101    |    200         | 2018-07-18 12:23:00
   102    |    283         | 2018-07-28 12:23:00

我需要上面的输出,其中仅显示最后两个更改在 unit_price 中发生。

2 个答案:

答案 0 :(得分:0)

这似乎很复杂:

SELECT t1.item_id,t1.unit_price,t1.created_date AS changed_date
FROM table_name t1 INNER JOIN 
   (
    SELECT a.item_id, a.unit_price, MAX(a.created_date) AS changed_date
    FROM table_name a INNER JOIN 
    (SELECT item_id, unit_price, MAX(created_date) AS changed_date
    FROM table_name GROUP BY item_id, unit_price) b
    ON a.item_id =  b.item_id and a.created_date < b.changed_date
    GROUP BY a.item_id, a.unit_price
   ) t2
   ON t1.item_id = t2.item_id AND t1.created_date >= t2.changed_date

答案 1 :(得分:0)

对于每个项目,您最多需要最后两个更改。在MySQL(V8之前的版本)中,您可以使用变量:

select t.*
from (select t.*,
             (@rn := if(@i = item_id, @rn + 1,
                        if(@i := item_id, 1, 1)
                       )
             ) as rn
      from (select t.*
            from t
            order by t.item_id, t.changed_date desc
           ) t cross join
           (select @i := -1, @rn := 0) params
     ) t
where rn <= 2;