(1) 窗函数的定义
日常生活中,根据业务需要,我们需要用到SQL的高级功能窗口函数
窗口函数:又称OLAP函数(在线分析处理),可以对数据库数据进行实时分析处理。 窗口函数的基本语法如下:
超过(通过
订购依据
语法里有什么? 在窗口函数的位置,可以放置以下两个函数:
1)特殊窗函数,包括rank、 、以及后面要提到的其他特殊窗函数
2)聚合函数,如sum、avg、count、max、min等。
因为窗口函数对where或group by子句处理后的结果进行操作,所以原则上窗口函数只能写在子句中。
(2) 窗函数的使用方法
1.特殊窗函数rank,如下面的类表
1)每个类内:按类排名,by用于对表格进行分组。 在这个例子中,我们指定按'class'(按类别)分组
2)按成绩排名:order by子句的作用是对分组结果进行排序。 默认是按照asc升序排序。 本例中(order desc)是按照grade列排序,并添加desc关键字。 表示降序排列。
如果想按照每个班级内的成绩进行排名,则需要执行以下SQL语句
如果使用group by + order by,结果如下。 我们发现group by在分组汇总后改变了表的行数,并且每一行只有一个类别。 by和rank函数不会减少原始表中的行数。
简单总结一下,窗口函数有以下几个功能:
1)同时具有分组和排序功能
2)不减少原表行数
3)语法如下:
超过(通过
订购依据
其他三个特殊窗口函数
特殊窗口函数包括:rank,,
他们的主要区别是:
从上面的结果可以看出:
Rank函数:本例中为4位、4位、4位、7位。 也就是说,如果存在排名并列的行,则它们将占据下一个排名位置。 例如,正常排名是1、2、3、4,但现在前3名并列,结果是,1、1、1、4。
功能:本例为4位,4位,4位,5位,即如果有并列排名的行,则不占据下一个排名位置。 例如,正常排名是1、2、3、4,但现在前3名并列,结果是1、1、1、2。
功能:本例为4位、5位、6位、7位,即排名并列的行不考虑。 比如前三名打平,排名正常为1、2、3、4。
需要强调的是:上述三个特殊窗口函数中,函数后面的括号不需要任何参数,只需将()留空即可。
四个经典面试排名问题
问题1:根据下面班级表的内容,按分数排序。 如果两个分数相同,则排名并列。
正常排名是1、2、3、4,但现在前3名打成平手,排名结果是:1、1、1、2。
最终的sql语句为:
问题2:根据下面的Score表,查询应该返回(按score从高到低排列)
最终的sql语句为:
五个经典面试TopN问题
TopN问题其实是一个常见的问题:分组取每组的最大值、最小值,以及每组最大的N条记录(Top N)。
1)分组并取每组的最大值
案例:按课程号分组,检索分数最高的行数据
首先使用group by和函数获取每门课程的最大值,但无法获取分数最高的行的数据。 如下:
我们可以使用相关子查询来做到这一点:
2)对每组的最小值进行分组
案例:按课程号分组,检索分数最低的行数据
3)每组最大的N条记录
案例:现有的“成绩表”记录了每个学生各科的成绩。 表的内容如下。 问题:找出每个学生得分最高的两门科目。
SQL语句解决问题
经典TopN问题:每组中最大的N条记录。 这类问题涉及到“既分组又排序”的情况,你一定能想到用窗口函数来实现。 如果修改本题的SQL语句(将where子句中的条件改为N),就可以成为此类题的通用模板。 如果你遇到这样的问题,可以直接使用:
# topN 问题 sql 模板 from ( *, () over ( 按要分组的列名 order 按要排序的列名 desc) as from 表名) as a where