Table: Project
±------------±--------+
| Column Name | Type |
±------------±--------+
| project_id | int |
| employee_id | int |
±------------±--------+
主键为 (project_id, employee_id)。
employee_id 是员工表 Employee 表的外键。
Table: Employee
±-----------------±--------+
| Column Name | Type |
±-----------------±--------+
| employee_id | int |
| name | varchar |
| experience_years | int |
±-----------------±--------+
主键是 employee_id。
编写一个SQL查询,报告所有雇员最多的项目。
查询结果格式如下所示:
Project table:
±------------±------------+
| project_id | employee_id |
±------------±------------+
| 1 | 1 |
| 1 | 2 |
| 1 | 3 |
| 2 | 1 |
| 2 | 4 |
±------------±------------+
Employee table:
±------------±-------±-----------------+
| employee_id | name | experience_years |
±------------±-------±-----------------+
| 1 | Khaled | 3 |
| 2 | Ali | 2 |
| 3 | John | 1 |
| 4 | Doe | 2 |
±------------±-------±-----------------+
Result table:
±------------+
| project_id |
±------------+
| 1 |
±------------+
第一个项目有3名员工,第二个项目有2名员工。
此处使用窗口函数较为简单,窗口函数用法如下:
窗口函数([<字段名>])over([partition by <分组字段>] [order by <排序字段>[desc]] [<窗口分区>])
partition by子句:按照指定字段进行分区,两个分区由边界分隔,窗口函数在不同的分区内分别执行,在跨越分区边界时重新初始化。
order by子句:按照指定字段进行排序,窗口函数将按照排序后的记录顺序进行编号。可以和partition by子句配合使用,也可以单独使用。
frame子句:当前分区的一个子集,用来定义子集的规则,通常用来作为滑动窗口使用。
此处先根据项目名字(project_id)的进行分组,然后使用窗口函数(dense_rank)进行排序,其它排序规则参考:https:///qq_40752621/article/details/126532785,将数据进行根据项目人员(employee_id )进行排序,然后再筛选人员排名第一的小组
如下:
select project_id
from (select project_id,
dense_rank() over(order by count(employee_id) decs) as ranking
from Project
group by project_id) as emp
where ranking = 1