【SQL】窗口函数的妙用

目录

语法

需求

示例

分析

代码


语法

开窗函数() over (partition by 列名 order by列名)

  • partition by: 需要分区的列
  • order by: 对分区内排序

连接函数concat(string1, string2, ..., stringN)

  • string1, string2, ..., stringN:是要连接的一个或多个字符串。

需求

Insurance 表:

复制代码
+-------------+-------+
| Column Name | Type  |
+-------------+-------+
| pid         | int   |
| tiv_2015    | float |
| tiv_2016    | float |
| lat         | float |
| lon         | float |
+-------------+-------+
pid 是这张表的主键(具有唯一值的列)。
表中的每一行都包含一条保险信息,其中:
pid 是投保人的投保编号。
tiv_2015 是该投保人在 2015 年的总投保金额,tiv_2016 是该投保人在 2016 年的总投保金额。
lat 是投保人所在城市的纬度。题目数据确保 lat 不为空。
lon 是投保人所在城市的经度。题目数据确保 lon 不为空。

编写解决方案报告 2016 年 (tiv_2016) 所有满足下述条件的投保人的投保金额之和:

  • 他在 2015 年的投保额 (tiv_2015) 至少跟一个其他投保人在 2015 年的投保额相同。
  • 他所在的城市必须与其他投保人都不同(也就是说 (lat, lon) 不能跟其他任何一个投保人完全相同)。

tiv_2016 四舍五入的 两位小数 。

示例 1:

复制代码
输入:
Insurance 表:
+-----+----------+----------+-----+-----+
| pid | tiv_2015 | tiv_2016 | lat | lon |
+-----+----------+----------+-----+-----+
| 1   | 10       | 5        | 10  | 10  |
| 2   | 20       | 20       | 20  | 20  |
| 3   | 10       | 30       | 20  | 20  |
| 4   | 10       | 40       | 40  | 40  |
+-----+----------+----------+-----+-----+
输出:
+----------+
| tiv_2016 |
+----------+
| 45.00    |
+----------+
解释:
表中的第一条记录和最后一条记录都满足两个条件。
tiv_2015 值为 10 与第三条和第四条记录相同,且其位置是唯一的。

第二条记录不符合任何一个条件。其 tiv_2015 与其他投保人不同,并且位置与第三条记录相同,这也导致了第三条记录不符合题目要求。
因此,结果是第一条记录和最后一条记录的 tiv_2016 之和,即 45 。

分析

编写解决方案报告 2016 年 (tiv_2016) 所有满足下述条件的投保人的投保金额之和:

多条件,考虑子查询、窗口函数等

他在 2015 年的投保额 (tiv_2015) 至少跟一个其他投保人在 2015 年的投保额相同。

至少跟另一个投保人在2015年的投保额度相同,换个角度,就是2015年同一投保额多于一人

通过窗口函数按照tiv2015分别计数,要求计数大于1即可实现,count(*) over(partition by tiv_2015) b

他所在的城市必须与其他投保人都不同(也就是说 (lat, lon) 不能跟其他任何一个投保人完全相同)。

城市必须与其他投保人都不同,即经纬度坐标不一样,换个角度,就是按照经纬度坐标分组,组内计数为1

同理可以通过窗口函数按照经纬度分别计数实现,这里需要注意concat的用法

CONCAT函数用于将两个或多个字符串值连接成一个字符串。

count(*) over(partition by concat(lat,lon)) a

在使用CONCAT函数时,如果任何参数为NULL,则行为可能因数据库而异。在MySQL和SQL Server中,CONCAT函数会忽略NULL值,但在其他数据库系统中可能需要特别处理。
字符串连接时,可能需要考虑空格或其他分隔符,以确保连接后的字符串易于阅读和理解。
某些数据库系统(如SQL Server)还提供了CONCAT_WS(CONCAT With Separator)函数,允许你指定一个分隔符来连接字符串,这在处理包含NULL值的字符串时特别有用。

代码

复制代码
select round(sum(tiv_2016),2) tiv_2016
from
(
    select *, 
    count(*) over(partition by concat(lat,lon)) a, 
    count(*) over(partition by tiv_2015) b
    from Insurance
) t
where a=1 and b>1
相关推荐
晋阳十二夜2 小时前
【压力测试之_Jmeter链接Oracle数据库链接】
数据库·oracle·压力测试
GDAL3 小时前
Node.js v22.5+ 官方 SQLite 模块全解析:从入门到实战
数据库·sqlite·node.js
DCTANT4 小时前
【原创】国产化适配-全量迁移MySQL数据到OpenGauss数据库
java·数据库·spring boot·mysql·opengauss
程序员岳焱6 小时前
Java 与 MySQL 性能优化:MySQL全文检索查询优化实践
后端·mysql·性能优化
喜欢敲代码的程序员6 小时前
SpringBoot+Mybatis+MySQL+Vue+ElementUI前后端分离版:项目搭建(一)
spring boot·mysql·elementui·vue·mybatis
AI、少年郎6 小时前
Oracle 进阶语法实战:从多维分析到数据清洗的深度应用(第四课)
数据库·oracle
赤橙红的黄7 小时前
自定义线程池-实现任务0丢失的处理策略
数据库·spring
钢铁男儿7 小时前
C# 委托(调用带引用参数的委托)
java·mysql·c#
叁沐7 小时前
MySQL 02 日志系统:一条SQL更新语句是如何执行的?
mysql
DataGear7 小时前
如何在DataGear 5.4.1 中快速制作SQL服务端分页的数据表格看板
javascript·数据库·sql·信息可视化·数据分析·echarts·数据可视化