【SQL】ROW_NUMBER() OVER(partition by 分组列 order by 排序列)用法详解+经典实例
#用法说明
select row_number() over(partition by A order by B ) as rowIndex from table
A :为分组字段
B:为分组后的排序字段。
table 表的结构 多为: 多人 多条的相关数据。(比如:订单信息)
此条sql语句,多用于对数据进行分组排序,并对每个组中的数据分别进行编号,编号从1开始递增,每个组内的编号不会重复;
#经典实例
0、填充数据
create table [OrderInfo](
[Id] [int] PRIMARY KEY IDENTITY(1,1) NOT NULL,
[UserId] [nvarchar](50) NOT NULL,
[TotalPrice] [float] NOT NULL,
[OrderTime] [datetime] NOT NULL,
); INSERT INTO [dbo].[OrderInfo]
([UserId]
,[TotalPrice]
,[OrderTime])
VALUES
(N'', 111, CAST(N'2011-01-01' AS DateTime)),
(N'', 112, CAST(N'2011-01-02' AS DateTime)),
(N'', 311, CAST(N'2013-01-01' AS DateTime)),
(N'', 312, CAST(N'2013-01-02' AS DateTime)),
(N'', 211, CAST(N'2012-01-01' AS DateTime)),
(N'', 212, CAST(N'2012-01-02' AS DateTime)),
(N'', 113, CAST(N'2011-01-03' AS DateTime)),
(N'', 213, CAST(N'2012-01-03' AS DateTime)),
(N'', 313, CAST(N'2013-01-03' AS DateTime))
GO
1、使用row_number()函数对订单进行编号,按照订单时间倒序。(此需求多用于分页)
select Id,UserId,TotalPrice,OrderTime,ROW_NUMBER() over (order by OrderTime desc) as rowIndex from OrderInfo

#分页场景:每页3条数据,取第2页
with
baseDate
as
(
select Id,UserId,TotalPrice,OrderTime,ROW_NUMBER() over (order by OrderTime desc) as rowIndex from OrderInfo
)
select * from baseDate where rowIndex>3 and rowIndex<7
2、所有订单按照客户进行分组,并按照客户下的订单的金额倒序排列。
select Id,UserId,orderTime,ROW_NUMBER() over(partition by UserId order by TotalPrice desc) as rowIndex from OrderInfo

3、筛选出客户第一次下的订单。
思路:利用rowIndex来判断订单是客户第几次下单;
with
baseDate
as
(
select Id,UserId,TotalPrice,orderTime,ROW_NUMBER() over (partition by UserId order by orderTime) as rowIndex from OrderInfo
)
select * from baseDate where rowIndex=1

4、筛选出客户在‘2011年1月1日之后的第一次下的订单。
思路:在分组排序之前进行实践筛选;
注意:在使用over等开窗函数时,over里头的分组及排序的执行晚于“where,group by,order by”的执行。
with
baseDate
as
(
select Id,UserId,TotalPrice,orderTime,ROW_NUMBER() over (partition by UserId order by orderTime) as rowIndex from OrderInfo
where OrderTime>'2011-1-1'
)
select * from baseDate where rowIndex=1

5、只保留每个客户的最近的一次订单,其余的订单删掉。(常用于删除重复数据)
with
baseDate
as
(
select Id,UserId,TotalPrice,OrderTime,ROW_NUMBER()over (partition by UserId order by OrderTime desc) as rowIndex from OrderInfo
)
delete from baseDate where rowIndex <> 1
6、统计每一个客户所有的订单中金额最大,并统计该订单是客户第几次购买;
思路:
1)先按照客户进行分组,然后按照客户下单的时间进行正序排列,并编号(rowIndex),生成临时表baseDate;
2)再按照客户进行分组,然后按照客户下单的金额进行倒序排列,并编号(rowIndex),生成临时表basePrice;
3)最后取basePrice中编号为1的数据,然后根据id到baseDate中去查,即可;
with
baseDate
as
(
select Id,UserId,TotalPrice,orderTime,ROW_NUMBER() over (partition by UserId order by orderTime) as rowIndex from OrderInfo
),
basePrice
as
(
select Id,UserId,orderTime,ROW_NUMBER() over(partition by UserId order by TotalPrice desc) as rowIndex from OrderInfo
)
select * from baseDate
where Id in (
select Id from basePrice where rowIndex=1
)

#图中的rowIndex字段就是该订单是第几次购买;
【SQL】ROW_NUMBER() OVER(partition by 分组列 order by 排序列)用法详解+经典实例的更多相关文章
- hive:数据库“行专列”操作---使用collect_set/collect_list/collect_all & row_number()over(partition by 分组字段 [order by 排序字段])
方案一:请参考<数据库“行专列”操作---使用row_number()over(partition by 分组字段 [order by 排序字段])>,该方案是sqlserver,orac ...
- 去重 ROW_NUMBER() OVER(PARTITION BY 分组字段 ORDER BY 排序字段) RN
关键字 ROW_NUMBER() OVER(PARTITION BY 分组字段 ORDER BY 排序字段) RN 按照分组字段进行排序并标编号 ROW_NUMBER() OVER(PARTITIO ...
- 数据库“行专列”操作---使用row_number()over(partition by 分组字段 [order by 排序字段])
测试样例: create table test(rsrp string,rsrq string,tkey string,distan string); '); '); '); '); select * ...
- SQL中的left outer join,inner join,right outer join用法详解
这两天,在研究SQL语法中的inner join多表查询语法的用法,通过学习,发现一个SQL命令,竟然涉及到很多线性代数方面的知识,现将这些知识系统地记录如下: 使用关系代数合并数据1 关系代数合并数 ...
- SQL学习笔记之SQL中INNER、LEFT、RIGHT JOIN的区别和用法详解
0x00 建表准备 相信很多人在刚开始使用数据库的INNER JOIN.LEFT JOIN和RIGHT JOIN时,都不太能明确区分和正确使用这三种JOIN操作,本文通过一个简单的例子通俗易懂的讲解这 ...
- oracle ROW_NUMBER() OVER(PARTITION BY '分组' ORDER BY '排序' DESC) 用法
转载:https://blog.csdn.net/dbagaoshou/article/details/51330829 SELECT * FROM ( SELECT ROW_NUMBER() OVE ...
- SQL row_number() over(partition by函数
1)row_number() over(partition by 列名1 order by 列名2 desc)的使用 表示根据 列名1 分组,然后在分组内部根据 列名2 排序,而此函数计算的值就表示每 ...
- row_number() over partition by 分组聚合
分组聚合,就是先分组再排序,可以的话顺手标个排名:如果不想分组也可以排名:如果不想分组同时再去重排名也可以 ROW_NUMBER() OVER( [PARTITION BY column_1, col ...
- SELECT a.loginname,a.deviceid,a.time,Row_Number() OVER (partition by a.loginname ORDER BY a.deviceid desc,a.time asc) rank
现在做一个反欺诈内容要用到笛卡尔积,用来分析用户一个手机号,对应的多个设备,每个更换设备的时间,这里取的时间是系统收集时间,用来代表更换的时间, 所以要先对设备换的时间作排序,然后进行rank,最后求 ...
随机推荐
- SQL常用语句(二)
--语 句 功 能--数据操作SELECT --从数据库表中检索数据行和列INSERT --向数据库表添加新数据行DELETE --从数据库表中删除数据行UPDATE --更新数据库表中的数据 --数 ...
- java class反编译工具----JD-GUI
下载地址 http://jd.benow.ca/
- Serial Splitter 4.2 串口拆分说明
使用方法 有些设备和程序只能使用COM端口.如果计算机没有COM端口,或者已经被其他应用程序占用,则需要创建虚拟串行端口.在串行分配器中,我们使用虚拟串行端口驱动程序技术,它可以在系统中创建任意数量的 ...
- 猴子吃桃儿问题(C#)
猴子第一天摘了许多个桃子,先吃了所有桃子的一半,后又吃了一个:第二天又吃了剩下桃子的一半,后又吃了一个……第十天,剩1个桃子.问:猴子第一天摘了多少个桃子? 本程序对其做了修改,天数和吃一半后又吃了一 ...
- extjs 中比较常见且好用的监听事件
ComboBox listeners:{ expand:function(){ //此函数是,点击下拉框展开的时候事件 }, select:function(com, record, index){ ...
- JVM内存结构简单认知
关于JVM的面试传送门:https://blog.csdn.net/shengmingqijiquan/article/details/77508471 JVM内存结构主要划分为:堆,jvm栈,本地方 ...
- 【spring源码分析】IOC容器初始化(十)
前言:前文[spring源码分析]IOC容器初始化(九)中分析了AbstractAutowireCapableBeanFactory#createBeanInstance方法中通过工厂方法创建bean ...
- Linux命令之常用篇
一.文件和目录 1. cd命令 它用于切换当前目录,它的参数是要切换到的目录的路径,可以是绝对路径,也可以是相对路径. 指令 说明 cd /home 进入‘home’目录 cd .. 返回上一级目录 ...
- Doctype知识点总结
DOCTYPE是document type (文档类型) 的缩写.<!DOCTYPE >声明位于文档的最前面,处于标签之前,它不是html标签.主要作用是告诉浏览器的解析器使用哪种HTML ...
- Cookie Session和自定义分页
cookie Cookie的由来 大家都知道HTTP协议是无状态的. 无状态的意思是每次请求都是独立的,它的执行情况和结果与前面的请求和之后的请求都无直接关系,它不会受前面的请求响应情况直接影响,也不 ...