【问题标题】:Additional condition withing partition over分区内的附加条件
【发布时间】:2019-02-25 11:00:59
【问题描述】:

https://www.db-fiddle.com/f/rgLXTu3VysD3kRwBAQK3a4/3

我的问题是我希望函数分区仅从特定时间范围开始计算行数。

在此示例中,如果我在末尾添加 rn = 1,则 order_id = 5 将从结果中排除(因为分区按 paid_date 排序,并且 order_id = 6 的日期较早)但它不应该就像我想要的那样,分区的时间范围从'2019-01-10'开始。

添加条件rn = 1预期输出应该是order_id 3,5,11,15,现在只有3,11,15

  • 它应该只包括给定时间范围内第一个带有is_paid = 0 的订单(如果之前有带有is_paid = 1 的订单,则不应计算在内)

【问题讨论】:

  • 你的预期输出是什么
  • 添加条件rn = 1,应该是order_id 3,5,11,15,现在是唯一的3,11,15 - 它应该只包括给定时间范围内第一个payed_status = 0的订单

标签: sql select


【解决方案1】:

将相关子查询与not exists一起使用

DEMO

 SELECT order_id, customer_id, amount, is_paid, paid_date,  rn FROM (
        SELECT o.*, 
            ROW_NUMBER() OVER(PARTITION BY customer_id ORDER BY paid_date,order_id) rn
        FROM orders o
         WHERE paid_date between '2019-01-10' 
    and '2019-01-15'
    ) x  where rn=1 and not exists (select 1 from orders o1 where x.order_id=o1.order_id
    and is_paid=1)

输出:

order_id    customer_id amount  is_paid paid_date      rn
3           101          30      0  10/01/2019 00:00:00 1
5           102          15      0  10/01/2019 00:00:00 1
11          104          31      0  10/01/2019 00:00:00 1
15          105          11      0  10/01/2019 00:00:00 1

【讨论】:

  • 感谢您的回答,无论如何,我是否遗漏了什么或者可以简化为:dbfiddle.uk/…(删除not exists 子查询并添加is_paid = 0 子句?)
【解决方案2】:

如果应该优先考虑 order_id,然后将其放在分区函数 order by 子句中的付款日期之前,这将解决您的问题。

SELECT order_id, customer_id, amount, is_paid, paid_date,  rn FROM (
            SELECT o.*, 
                ROW_NUMBER() OVER(PARTITION BY customer_id ORDER BY  order_id,paid_date) rn
            FROM orders o
        ) x WHERE is_paid = 0 and paid_date between 
        '2019-01-10' and '2019-01-15' and rn=1

由于您需要首先订购付款日期,因此您需要在分区表中暗示 where 条件,以避免不必要的日期中断分区功能。

SELECT order_id, customer_id, amount, is_paid, paid_date,  rn FROM (
        SELECT o.*, 
            ROW_NUMBER() OVER(PARTITION BY customer_id ORDER BY paid_date, order_id) rn
        FROM orders o
  where paid_date between '2019-01-10' and '2019-01-15'
    ) x WHERE is_paid = 0 and rn=1

【讨论】:

  • 我故意在order by中使用了paid_date,应该在date上先下单,如果order_id相同,则不然
猜你喜欢
  • 2017-12-25
  • 1970-01-01
  • 1970-01-01
  • 2012-08-28
  • 1970-01-01
  • 2018-08-01
  • 1970-01-01
  • 1970-01-01
  • 2021-11-16
相关资源
最近更新 更多