简体   繁体   English

SQL 雪花 - 在一张表中比较 2 个日期

[英]SQL Snowflake - Compare 2 dates in one table

I have the following table我有下表

card id | txn id | date | legit
 xys       txq      Mar.1  1
 xys       txs      Mar.8  0
 xys       txt      Mar.12 0
 xyb       txl      Mar.13 0
 xyb       txp      Mar.14 1

I want to be able to compare the date between the first record and any future records for that card id where that future record's legit = 0, and if the first record is within 10 days, show that record.我希望能够比较第一条记录与该卡 ID 的任何未来记录之间的日期,其中未来记录的合法性 = 0,如果第一条记录在 10 天内,则显示该记录。 (note this would also need to include the first record if legit = 0). (请注意,如果 legit = 0,这也需要包括第一条记录)。

If there is a better way to think about this problem, I'm all ears.如果有更好的方法来思考这个问题,我会全力以赴。 I'm pretty sure dateddiff will come in use here but I'm not sure how to make the comparison between the 1st record and any future record.我很确定dateddiff会在这里使用,但我不确定如何在第一条记录和任何未来记录之间进行比较。

Example output would be:示例 output 将是:

card id | txn id | date | legit
xys       txs      Mar.8  0
xyb       txl     Mar.13  0

WHERE legit = 0...

There might be a more efficient way to do this, but I think this gets you what you are asking for:可能有一种更有效的方法可以做到这一点,但我认为这可以满足您的要求:

WITH x AS (
    SELECT *
    FROM (VALUES 
          ('xys','txq','2020-03-01'::DATE,1),
          ('xys','txs','2020-03-08'::DATE,0),
          ('xys','txt','2020-03-12'::DATE,0),
          ('xyb','txl','2020-03-13'::DATE,0),
          ('xyb','txp','2020-03-14'::DATE,1)) as y (card_id, txn_id, date_, legit)
    )
SELECT card_id,
    CASE WHEN legit = 0 THEN txn_id
         WHEN DATEDIFF('d',date_next,date_) <= 10 THEN txn_id_next
         ELSE txn_id END as txn_id,
    CASE WHEN legit = 0 THEN date_
         WHEN DATEDIFF('d',date_next,date_) <= 10 THEN date_next
         ELSE date_ END as date_,   
    CASE WHEN legit = 0 THEN legit
         WHEN DATEDIFF('d',date_next,date_) <= 10 THEN legit_next
         ELSE legit END as legit
FROM (
  SELECT *,
      ROW_NUMBER() OVER (PARTITION BY card_id ORDER BY date_) as row_num,
      LEAD(txn_id) OVER (PARTITION BY card_id ORDER BY date_) as txn_id_next,
      LEAD(date_) OVER (PARTITION BY card_id ORDER BY date_) as date_next,
      LEAD(legit) OVER (PARTITION BY card_id ORDER BY date_) as legit_next
  FROM x
  QUALIFY row_num = 1
  );

This first gets the first record and the "next record" and moves them to a single line, and then the CASE statements determine whether to use the first record or the "next" record based on the rules that I think you specified.这首先获取第一条记录和“下一条记录”并将它们移动到单行,然后CASE语句根据我认为您指定的规则确定是使用第一条记录还是“下一条”记录。

I want to be able to compare the date between the first record and any future records for that card id where that future record's legit = 0, and if the first record is within 10 days, show that record.我希望能够比较第一条记录与该卡 ID 的任何未来记录之间的日期,其中未来记录的合法性 = 0,如果第一条记录在 10 天内,则显示该记录。

If I understand correctly, you can use window functions:如果我理解正确,您可以使用 window 函数:

select t.*
from (select t.*, min(date) over (partition by cardid) as min_date
      from t
     ) t
where legit = 0 and date < min_date + interval '10 day';

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM