leetcode 数据库题
- 175. 组合两个表
- 176. 第二高的薪水
- 177. 第N高的薪水
- 178. 分数排名
- 180. 连续出现的数字
- 181. 超过经理收入的员工
- 182. 查找重复的电子邮箱
- 183. 从不订购的客户
- 184. 部门工资最高的员工
- 185. 部门工资前三高的所有员工
- 小结
嗯。。。数据库题目就不贴原题内容了,表结构贴过来也不好看。
CSDN 文盲老顾的博客,https://blog.csdn.net/superwfei
175. 组合两个表
题目地址:https://leetcode.cn/problems/combine-two-tables/submissions/
简单来说,就是考察 join 的使用,简单题目。同时,需要指定列集合,应该没有小伙伴不会吧。leetcode 支持的三种 sql 都可以用一个指令完成操作。
select firstName,lastName,city,state
from person a
left join address b on a.personid=b.personid
176. 第二高的薪水
题目地址:https://leetcode.cn/problems/second-highest-salary/
嗯,这题有个小坑,当没有数据的时候,其实应该输出一个 null,所以。。。。
还有就是。。。第二高,所以不能用row_number,要用 dense_rank
select (
select salary
from (
select distinct salary,dense_rank() over(order by salary desc) rid
from employee
) a
where rid=2
) SecondHighestSalary
oracle 不熟,不知道为什么这个指令不能运行
177. 第N高的薪水
题目地址:https://leetcode.cn/problems/nth-highest-salary/
额。。。和刚才的题目几乎一模一样啊,把2改成变量 @n 就好
mysql
CREATE FUNCTION getNthHighestSalary(N INT) RETURNS INT
BEGIN
RETURN (
# Write your MySQL query statement below.
select distinct salary
from (
select salary,dense_rank() over(order by salary desc) rid
from employee
) a
where rid=N
);
END
sqlserver
CREATE FUNCTION getNthHighestSalary(@N INT) RETURNS INT AS
BEGIN
RETURN (
/* Write your T-SQL query statement below. */
select distinct salary
from (
select salary,dense_rank() over(order by salary desc) rid
from employee
) a
where rid=@N
);
END
当然,mysql 这个题目还是有优势的,用 limit 更效率一些
178. 分数排名
题目地址:https://leetcode.cn/problems/rank-scores/
嗯,标准的考 dense_rank 的用法的题目。
mssql
select score,dense_rank() over(order by score desc) as rank from scores
mysql
select score,dense_rank() over(order by score desc) 'rank' from scores;
mysql 需要注意列名需要加修饰即可
180. 连续出现的数字
题目地址:https://leetcode.cn/problems/consecutive-numbers/
嗯,多次 row_number 组合即可,最后记得排重
select distinct num ConsecutiveNums
from (
select *
,row_number() over(order by id) rid
,row_number() over(partition by num order by id) nid
from logs
) a
group by rid - nid,num
having(count(0) > 2)
181. 超过经理收入的员工
题目地址:https://leetcode.cn/problems/employees-earning-more-than-their-managers/
考察一下自关联,inner join 即可,指令一拖三没问题。
select a.name Employee
from employee a
inner join employee b on a.managerid=b.id
where a.salary > b.salary
182. 查找重复的电子邮箱
题目地址:https://leetcode.cn/problems/duplicate-emails/
又是一个基础题目,考察 group 时 having 的使用
select email from person group by email having(count(0)>1)
183. 从不订购的客户
题目地址:https://leetcode.cn/problems/customers-who-never-order/
看题目的意思,用个 not exists 就好
select name Customers
from customers a
where not exists(select 1 from orders where customerid=a.id)
184. 部门工资最高的员工
题目地址:https://leetcode.cn/problems/department-highest-salary/
很明显,row_number 结合 partition 最方便。然后看了看示例,有重复数据,那就换 rank就好。
select b.name department,a.name employee,salary
from (
select *,rank() over(partition by departmentid order by salary desc) rid
from employee
) a
left join department b on a.departmentid=b.id
where rid=1
oracle 的开窗函数也许有细节的不同,回头再研究。
185. 部门工资前三高的所有员工
题目地址:https://leetcode.cn/problems/department-top-three-salaries/
其实和前一个题目没什么区别,rank 换成 dense_rank?然后 rid=1 变成 rid<4?
select b.name department,a.name employee,salary
from (
select *,dense_rank() over(partition by departmentid order by salary desc) rid
from employee
) a
left join department b on a.departmentid=b.id
where rid<4
说起来,排名函数,sqlserver 从 2005 版本就已经支持起来了,mysql 支持的倒是比较晚,mysql 8 才支持,2016年才出的。也许这些题目考的不是排名函数?
试着不用排名函数做一版出来。
select c.name department,b.name employee,a.salary
from (
select distinct departmentid,salary
from employee a
where (
select count(0)
from (
select distinct salary
from employee
where departmentid=a.departmentid and salary > a.salary
) x
) < 3
) a
left join employee b on a.departmentid=b.departmentid and a.salary=b.salary
left join department c on a.departmentid=c.id
小结
CSDN 文盲老顾的博客,https://blog.csdn.net/superwfei
嗯,后边的数据库题,题号不连续了,估计算法题也会出现不连续的情况了。。。今天就先刷到这里。
总的来说,这些数据库题目都不是难题,一些基础的查询指令熟练的话,基本都能很快的做出来。
而因为 leetcode 的 mysql 版本,已经是 8 了,所以很多新特性是可以使用的,比如 cte 之类的。当然,仅仅是在有必要的情况下取用哦。
对于 select 的基础查询,各个教程,各个官方文档里都有相吸说明,老顾就不再重复了。一定要看官方的文档最优先哦。
至于算法题。。。。老顾是卡在树那里了,毕竟老顾自己工作中,完全没有接触过树和图的算法。。。。还在补课中。。。被自己蠢死了。。。。