当前位置: 首页 > news >正文

SQL面试题练习 —— 查询最近一笔有效订单

目录

  • 1 题目
  • 2 建表语句
  • 3 题解

题目来源:字节跳动。

1 题目


现有订单表t_order,包含订单ID,订单时间,下单用户,当前订单是否有效,请查询出每个用户每笔订单的上一笔有效订单

+---------+----------------------+----------+-----------+
| ord_id  |       ord_time       | user_id  | is_valid  |
+---------+----------------------+----------+-----------+
| 1       | 2023-12-11 12:01:03  | a        | 1         |
| 2       | 2023-12-11 12:02:06  | a        | 0         |
| 3       | 2023-12-11 12:03:15  | a        | 0         |
| 4       | 2023-12-11 12:04:20  | a        | 1         |
| 5       | 2023-12-11 12:05:03  | a        | 1         |
| 6       | 2023-12-11 12:01:02  | b        | 1         |
| 7       | 2023-12-11 12:03:03  | b        | 0         |
| 8       | 2023-12-11 12:04:01  | b        | 1         |
| 9       | 2023-12-11 12:07:03  | b        | 1         |
+---------+----------------------+----------+-----------+

期望查询结果如下:

+---------+----------------------+----------+-----------+--------------------+
| ord_id  |       ord_time       | user_id  | is_valid  | last_valid_ord_id  |
+---------+----------------------+----------+-----------+--------------------+
| 1       | 2023-12-11 12:01:03  | a        | 1         | NULL               |
| 2       | 2023-12-11 12:02:06  | a        | 0         | 1                  |
| 3       | 2023-12-11 12:03:15  | a        | 0         | 1                  |
| 4       | 2023-12-11 12:04:20  | a        | 1         | 1                  |
| 5       | 2023-12-11 12:05:03  | a        | 1         | 4                  |
| 6       | 2023-12-11 12:01:02  | b        | 1         | NULL               |
| 7       | 2023-12-11 12:03:03  | b        | 0         | 6                  |
| 8       | 2023-12-11 12:04:01  | b        | 1         | 6                  |
| 9       | 2023-12-11 12:07:03  | b        | 1         | 8                  |
+---------+----------------------+----------+-----------+--------------------+

2 建表语句


--建表语句
create table t_order
(
ord_id bigint COMMENT '订单ID',
ord_time string COMMENT '订单时间',
user_id string COMMENT '用户',
is_valid bigint COMMENT '订单是否有效'
) COMMENT '订单记录表'
stored as orc
;
-- 数据插入
insert into t_order(ord_id,ord_time,user_id,is_valid)
values
(1,'2023-12-11 12:01:03','a',1),
(2,'2023-12-11 12:02:06','a',0),
(3,'2023-12-11 12:03:15','a',0),
(4,'2023-12-11 12:04:20','a',1),
(5,'2023-12-11 12:05:03','a',1),
(6,'2023-12-11 12:01:02','b',1),
(7,'2023-12-11 12:03:03','b',0),
(8,'2023-12-11 12:04:01','b',1),
(9,'2023-12-11 12:07:03','b',1);

3 题解


(1)先查询出有效订单,然后计算出每笔有效订单的上一单有效订单;

select ord_id,ord_time,user_id,is_valid,lag(ord_id) over (partition by user_id order by ord_time asc) as last_valid_ord_id
from (select ord_id,ord_time,user_id,is_validfrom t_orderwhere is_valid = 1) t

执行结果

+---------+----------------------+----------+-----------+--------------------+
| ord_id  |       ord_time       | user_id  | is_valid  | last_valid_ord_id  |
+---------+----------------------+----------+-----------+--------------------+
| 1       | 2023-12-11 12:01:03  | a        | 1         | NULL               |
| 4       | 2023-12-11 12:04:20  | a        | 1         | 1                  |
| 5       | 2023-12-11 12:05:03  | a        | 1         | 4                  |
| 6       | 2023-12-11 12:01:02  | b        | 1         | NULL               |
| 8       | 2023-12-11 12:04:01  | b        | 1         | 6                  |
| 9       | 2023-12-11 12:07:03  | b        | 1         | 8                  |
+---------+----------------------+----------+-----------+--------------------+

(2)原始的明细数据与新的有效订单表按照用户进行关联,有效订单表的订单时间大于等于原始订单表;

with tmp as (-- 有效订单及其上一单有效记录select ord_id,ord_time,user_id,is_valid,lag(ord_id) over (partition by user_id order by ord_time asc) as last_valid_ord_idfrom (select ord_id,ord_time,user_id,is_validfrom t_orderwhere is_valid = 1) t)
select t1.*,t2.*
from t_order t1
left join tmp t2
on t1.user_id = t2.user_id
where t1.ord_time <= t2.ord_time

执行结果

+------------+----------------------+-------------+--------------+------------+----------------------+-------------+--------------+-----------------------+
| t1.ord_id  |     t1.ord_time      | t1.user_id  | t1.is_valid  | t2.ord_id  |     t2.ord_time      | t2.user_id  | t2.is_valid  | t2.last_valid_ord_id  |
+------------+----------------------+-------------+--------------+------------+----------------------+-------------+--------------+-----------------------+
| 1          | 2023-12-11 12:01:03  | a           | 1            | 1          | 2023-12-11 12:01:03  | a           | 1            | NULL                  |
| 1          | 2023-12-11 12:01:03  | a           | 1            | 4          | 2023-12-11 12:04:20  | a           | 1            | 1                     |
| 2          | 2023-12-11 12:02:06  | a           | 0            | 4          | 2023-12-11 12:04:20  | a           | 1            | 1                     |
| 3          | 2023-12-11 12:03:15  | a           | 0            | 4          | 2023-12-11 12:04:20  | a           | 1            | 1                     |
| 4          | 2023-12-11 12:04:20  | a           | 1            | 4          | 2023-12-11 12:04:20  | a           | 1            | 1                     |
| 1          | 2023-12-11 12:01:03  | a           | 1            | 5          | 2023-12-11 12:05:03  | a           | 1            | 4                     |
| 2          | 2023-12-11 12:02:06  | a           | 0            | 5          | 2023-12-11 12:05:03  | a           | 1            | 4                     |
| 3          | 2023-12-11 12:03:15  | a           | 0            | 5          | 2023-12-11 12:05:03  | a           | 1            | 4                     |
| 4          | 2023-12-11 12:04:20  | a           | 1            | 5          | 2023-12-11 12:05:03  | a           | 1            | 4                     |
| 5          | 2023-12-11 12:05:03  | a           | 1            | 5          | 2023-12-11 12:05:03  | a           | 1            | 4                     |
| 6          | 2023-12-11 12:01:02  | b           | 1            | 6          | 2023-12-11 12:01:02  | b           | 1            | NULL                  |
| 6          | 2023-12-11 12:01:02  | b           | 1            | 8          | 2023-12-11 12:04:01  | b           | 1            | 6                     |
| 7          | 2023-12-11 12:03:03  | b           | 0            | 8          | 2023-12-11 12:04:01  | b           | 1            | 6                     |
| 8          | 2023-12-11 12:04:01  | b           | 1            | 8          | 2023-12-11 12:04:01  | b           | 1            | 6                     |
| 6          | 2023-12-11 12:01:02  | b           | 1            | 9          | 2023-12-11 12:07:03  | b           | 1            | 8                     |
| 7          | 2023-12-11 12:03:03  | b           | 0            | 9          | 2023-12-11 12:07:03  | b           | 1            | 8                     |
| 8          | 2023-12-11 12:04:01  | b           | 1            | 9          | 2023-12-11 12:07:03  | b           | 1            | 8                     |
| 9          | 2023-12-11 12:07:03  | b           | 1            | 9          | 2023-12-11 12:07:03  | b           | 1            | 8                     |
+------------+----------------------+-------------+--------------+------------+----------------------+-------------+--------------+-----------------------+

(3)使用row_number,原始订单记录表中的user_id、ord_id进行分组,按照有效订单表的时间排序,增加分组排序

with tmp as (-- 有效订单及其上一单有效记录select ord_id,ord_time,user_id,is_valid,lag(ord_id) over (partition by user_id order by ord_time asc) as last_valid_ord_idfrom (select ord_id,ord_time,user_id,is_validfrom t_orderwhere is_valid = 1) t)
select t1.*,t2.*,row_number() over (partition by t1.ord_id,t1.user_id order by t2.ord_time asc) as rn
from t_order t1
left join tmp t2
on t1.user_id = t2.user_id
where t1.ord_time <= t2.ord_time

执行结果

+------------+----------------------+-------------+--------------+------------+----------------------+-------------+--------------+-----------------------+-----+
| t1.ord_id  |     t1.ord_time      | t1.user_id  | t1.is_valid  | t2.ord_id  |     t2.ord_time      | t2.user_id  | t2.is_valid  | t2.last_valid_ord_id  | rn  |
+------------+----------------------+-------------+--------------+------------+----------------------+-------------+--------------+-----------------------+-----+
| 1          | 2023-12-11 12:01:03  | a           | 1            | 1          | 2023-12-11 12:01:03  | a           | 1            | NULL                  | 1   |
| 1          | 2023-12-11 12:01:03  | a           | 1            | 4          | 2023-12-11 12:04:20  | a           | 1            | 1                     | 2   |
| 1          | 2023-12-11 12:01:03  | a           | 1            | 5          | 2023-12-11 12:05:03  | a           | 1            | 4                     | 3   |
| 2          | 2023-12-11 12:02:06  | a           | 0            | 4          | 2023-12-11 12:04:20  | a           | 1            | 1                     | 1   |
| 2          | 2023-12-11 12:02:06  | a           | 0            | 5          | 2023-12-11 12:05:03  | a           | 1            | 4                     | 2   |
| 3          | 2023-12-11 12:03:15  | a           | 0            | 4          | 2023-12-11 12:04:20  | a           | 1            | 1                     | 1   |
| 3          | 2023-12-11 12:03:15  | a           | 0            | 5          | 2023-12-11 12:05:03  | a           | 1            | 4                     | 2   |
| 4          | 2023-12-11 12:04:20  | a           | 1            | 4          | 2023-12-11 12:04:20  | a           | 1            | 1                     | 1   |
| 4          | 2023-12-11 12:04:20  | a           | 1            | 5          | 2023-12-11 12:05:03  | a           | 1            | 4                     | 2   |
| 5          | 2023-12-11 12:05:03  | a           | 1            | 5          | 2023-12-11 12:05:03  | a           | 1            | 4                     | 1   |
| 6          | 2023-12-11 12:01:02  | b           | 1            | 6          | 2023-12-11 12:01:02  | b           | 1            | NULL                  | 1   |
| 6          | 2023-12-11 12:01:02  | b           | 1            | 8          | 2023-12-11 12:04:01  | b           | 1            | 6                     | 2   |
| 6          | 2023-12-11 12:01:02  | b           | 1            | 9          | 2023-12-11 12:07:03  | b           | 1            | 8                     | 3   |
| 7          | 2023-12-11 12:03:03  | b           | 0            | 8          | 2023-12-11 12:04:01  | b           | 1            | 6                     | 1   |
| 7          | 2023-12-11 12:03:03  | b           | 0            | 9          | 2023-12-11 12:07:03  | b           | 1            | 8                     | 2   |
| 8          | 2023-12-11 12:04:01  | b           | 1            | 8          | 2023-12-11 12:04:01  | b           | 1            | 6                     | 1   |
| 8          | 2023-12-11 12:04:01  | b           | 1            | 9          | 2023-12-11 12:07:03  | b           | 1            | 8                     | 2   |
| 9          | 2023-12-11 12:07:03  | b           | 1            | 9          | 2023-12-11 12:07:03  | b           | 1            | 8                     | 1   |
+------------+----------------------+-------------+--------------+------------+----------------------+-------------+--------------+-----------------------+-----+

(4)去除冗余字段,筛选rn=1 的记录

with tmp as (-- 有效订单及其上一单有效记录select ord_id,ord_time,user_id,is_valid,lag(ord_id) over (partition by user_id order by ord_time asc) as last_valid_ord_idfrom (select ord_id,ord_time,user_id,is_validfrom t_orderwhere is_valid = 1) t)
select *
from (select t1.*,t2.last_valid_ord_id,row_number() over (partition by t1.ord_id,t1.user_id order by t2.ord_time asc) as rnfrom t_order t1left join tmp t2on t1.user_id = t2.user_idwhere t1.ord_time <= t2.ord_time) tt
where rn = 1

执行结果

+------------+----------------------+-------------+--------------+-----------------------+--------+
| tt.ord_id  |     tt.ord_time      | tt.user_id  | tt.is_valid  | tt.last_valid_ord_id  | tt.rn  |
+------------+----------------------+-------------+--------------+-----------------------+--------+
| 1          | 2023-12-11 12:01:03  | a           | 1            | NULL                  | 1      |
| 2          | 2023-12-11 12:02:06  | a           | 0            | 1                     | 1      |
| 3          | 2023-12-11 12:03:15  | a           | 0            | 1                     | 1      |
| 4          | 2023-12-11 12:04:20  | a           | 1            | 1                     | 1      |
| 5          | 2023-12-11 12:05:03  | a           | 1            | 4                     | 1      |
| 6          | 2023-12-11 12:01:02  | b           | 1            | NULL                  | 1      |
| 7          | 2023-12-11 12:03:03  | b           | 0            | 6                     | 1      |
| 8          | 2023-12-11 12:04:01  | b           | 1            | 6                     | 1      |
| 9          | 2023-12-11 12:07:03  | b           | 1            | 8                     | 1      |
+------------+----------------------+-------------+--------------+-----------------------+--------+
http://www.lryc.cn/news/385599.html

相关文章:

  • 分享HTML显示2D/3D粒子时钟
  • Java——IDEA使用
  • 高性能STL库 EASTL 、高性能JSON库
  • 多通道采集器采样接口设计[进行中...]
  • rapidjson使用中crash问题分析
  • TCP协议中的三次握手和四次挥手机制
  • Linux双网卡默认路由的metric设置不正确,导致SSH连接失败问题定位
  • Batch入门学习:从零开始掌握批处理脚本
  • diffusion model(十八):diffusion model中negative prompt的工作机制
  • Python | Leetcode Python题解之第200题岛屿数量
  • 利用圆上两点和圆半径求解圆心坐标
  • 从ChatGPT代码执行逃逸到LLMs应用安全思考
  • Python入门-基础知识-变量
  • 设计模式原则——接口隔离原则
  • MySQL数据库——在Centos7环境安装
  • 怎样规避液氮容器内部结霜的问题
  • 冶金工业5G智能工厂工业物联数字孪生平台,推进制造业数字化转型
  • 一文入门机器学习参数调整实操
  • 基于51单片机的银行排队呼叫系统设计
  • JXCategoryView的使用总结
  • Centos9 安装VBox增强功能问题
  • 【JVM】Java虚拟机运行时数据分区介绍
  • 大数据面试题之Kafka(2)
  • 前端面试题(基础篇十一)
  • 【论文阅读】Answering Label-Constrained Reachability Queries via Reduction Techniques
  • Git Flow 工作流学习要点
  • blender 快捷键 常见问题
  • HTTP详解:TCP三次握手和四次挥手
  • 详解HTTP:有了HTTP,为何需要WebSocket?
  • Spring Boot 启动流程是怎么样的