【问题标题】:How to get the value from table B whose max date is less than the date in table A如何从最大日期小于表 A 中日期的表 B 中获取值
【发布时间】:2020-03-18 11:20:28
【问题描述】:

我有两张桌子;表 A 和表 B。表 A 有 StoreNumber、MatNumber 和 Date。表 B 有 StoreNumber、MatNumber、Date 和 ShipmentValue。我必须从表 B 中获取 StoreNumber 和 MatNumber 的 Shipment 值,因为表 B 中 StoreNumber 和 MatNumber 的最大日期应小于表 A 中相同 StoreNumber 和 MatNumber 的日期(表 A 中的每一行)。请看输出表。

表 A:

StoreNumber MatNumber   Date
  A            9    3/30/2020
  A            9    3/30/2020
  B           10    3/18/2020
  B           10    3/18/2020
  A            9    3/13/2020

表 B:

StoreNumber MatNumber   Date    ShipmentValue
       A           9    3/10/2020   2
       A           9    3/12/2020   3
       A           9    3/18/2020   4
       B          10    3/4/2020    7
       B          10    3/7/2020    9
       B          10    3/16/2020   10

输出:

StoreNumber MatNumber   A.Date  B.Date  ShipmentValue
       A           9    3/30/2020   3/18/2020   4
       A           9    3/30/2020   3/18/2020   4
       B          10    3/18/2020   3/16/2020   10
       B          10    3/18/2020   3/16/2020   10
       A           9    3/13/2020   3/12/2020   3

【问题讨论】:

    标签: sql snowflake-cloud-data-platform


    【解决方案1】:

    尝试使用 ROW_NUMBER 并在按 desc 订购日期后选择第一行。

    SELECT  A.StoreNumber 
            ,A.MatNumber  
            ,A.Date 
            ,B.Date AS B_Date   
            ,B.ShipmentValue 
    FROM    TableA A
    LEFT JOIN 
            (
              SELECT  StoreNumber ,MatNumber  , Date   , ShipmentValue
              FROM 
                  (
                    SELECT ROW_NUMBER() OVER (PARTITION BY StoreNumber, MatNumber ORDER BY DATE DESC ) AS ID,* 
                    FROM TableB
                  ) A 
              WHERE ID = 1
             ) B
    ON   A.StoreNumber  = B.StoreNumber
    AND  A.MatNumber    = B.MatNumber
    

    【讨论】:

      【解决方案2】:

      这是一个方便lateral join 的地方:

      select a.*, b.date, b.shipmentvalue
      from a left join lateral
           (select b.*
            from b
            where b.storenumber = a.storenumber and
                  b.matnumber = a.matnumber and
                  b.date <= a.date
            order by b.date desc
            fetch first 1 row only
           ) b
           on 1=1;  -- returns rows in a even when there are no matches
      

      编辑:

      哇。 Snowflake 实现横向连接,然后以基本方式限制它们。另一种方法更昂贵但应该有效:

      select ab.*, b.shipmentValue
      from (select a.StoreNumber, a.MatNumber, a.Date, max(b.date) as b_date, b.shipmentvalue
            from a left join
                 b 
                 on b.storenumber = a.storenumber and
                    b.matnumber = a.matnumber and
                    b.date <= a.date
            group by a.StoreNumber, a.MatNumber, a.Date
           ) ab join
           b
           on b.storenumber = ab.storenumber and
              b.matnumber = ab.matnumber and
              b.date <= ab.b_date
      

      【讨论】:

      • 感谢您的回复。我收到以下错误:SQL 编译错误:无法评估不支持的子查询类型。 Snowflake 是否支持此查询?
      • 看起来 Snowflake 不支持 from a left join lateral。试试改成from a, lateral (
      • 问题是由于仅获取前 1 行而出现的。当我评论它时,查询正在运行。我什至尝试了限制 1,但它抛出了同样的错误。
      • @Ashish 。 . .这真是令人不安。它们支持横向连接,但不完全支持——并且没有记录。
      猜你喜欢
      • 2018-03-12
      • 2020-09-08
      • 1970-01-01
      • 1970-01-01
      • 2019-02-03
      • 2019-03-01
      • 2010-12-11
      • 2019-06-21
      • 1970-01-01
      相关资源
      最近更新 更多