PostgreSQL查询:状态为null且上一步状态为done的订单记录
满足指定条件的SQL查询方案
需求对应逻辑
需要筛选出同时符合以下两个条件的记录,最后按order字段分组:
- 当前记录的
status为null - 同一
order下,step_no比当前记录小1的上一步记录,其status为"done"
方案1:自连接写法(兼容多数SQL数据库)
这种写法适用于几乎所有支持SQL的数据库,逻辑直观易懂:
SELECT t1.* FROM your_table t1 JOIN your_table t2 ON t1.`order` = t2.`order` AND t1.step_no = t2.step_no + 1 WHERE t1.status IS NULL AND t2.status = 'done' GROUP BY t1.`order`;
说明:
- 通过自连接关联同一张表,
t1.order= t2.order``确保是同一订单的记录,t1.step_no = t2.step_no +1锁定t2是t1的上一步记录 - 筛选条件直接匹配需求:t1(当前记录)status为null,t2(上一步记录)status为done
GROUP BY t1.order``实现按订单分组,若需要每个订单只展示特定字段,可结合聚合函数(比如MAX(t1.step_no))调整
方案2:窗口函数写法(适用于支持窗口函数的数据库)
如果你的数据库支持窗口函数(如MySQL 8+、PostgreSQL、SQL Server等),可以用更简洁的方式实现:
WITH step_prev_status AS ( SELECT *, LAG(status) OVER (PARTITION BY `order` ORDER BY step_no) AS prev_step_status FROM your_table ) SELECT * FROM step_prev_status WHERE status IS NULL AND prev_step_status = 'done' GROUP BY `order`;
说明:
- 用
LAG()窗口函数,按order分组、step_no排序,自动获取每条记录的上一步status,命名为prev_step_status - 直接筛选当前记录
status为null且上一步status为done的结果,最后按order分组
注意事项
- 把SQL中的
your_table替换成你实际使用的表名 - 由于
order是SQL关键字,需要用反引号(`)包裹,不同数据库的关键字转义规则可能不同,可根据实际情况调整 - 分组后若要展示非分组字段,需配合聚合函数使用,符合SQL的分组规则
内容的提问来源于stack exchange,提问作者KeanHo Leong
相关产品推荐
相关产品推荐

