组合两个表

编写一个SQL查询来报告 Person 表中每个人的姓、名、城市和州。如果 personId 的地址不在 Address 表中,则报告为空 null 。以 任意顺序 返回结果表。

案例

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
输入: 
Person表:
+----------+----------+-----------+
| personId | lastName | firstName |
+----------+----------+-----------+
| 1 | Wang | Allen |
| 2 | Alice | Bob |
+----------+----------+-----------+
Address表:
+-----------+----------+---------------+------------+
| addressId | personId | city | state |
+-----------+----------+---------------+------------+
| 1 | 2 | New York City | New York |
| 2 | 3 | Leetcode | California |
+-----------+----------+---------------+------------+
输出:
+-----------+----------+---------------+----------+
| firstName | lastName | city | state |
+-----------+----------+---------------+----------+
| Allen | Wang | Null | Null |
| Bob | Alice | New York City | New York |
+-----------+----------+---------------+----------+
解释:
地址表中没有 personId = 1 的地址,所以它们的城市和州返回 null。
addressId = 1 包含了 personId = 2 的地址信息。

CodeDemo

1
2
3
4
5
6
select 
firstName,
lastName,
city,
state
from Person p left join Address a on p.personId = a.personId

第N高的薪水

查询 Employee 表中第 n 高的工资。如果没有第 n 个最高工资,查询结果应该为 null

示例

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
输入: 
Employee table:
+----+--------+
| id | salary |
+----+--------+
| 1 | 100 |
| 2 | 200 |
| 3 | 300 |
+----+--------+
n = 2
输出:
+------------------------+
| getNthHighestSalary(2) |
+------------------------+
| 200 |
+------------------------+

CodeDemo

1
2
3
4
5
6
7
with tmp as (
select
distinct salary,
dense_rank() over(order by salary desc) as rk
from Employee
)
select salary from tmp where rk = N

分数排名

表: Scores

1
2
3
4
5
6
7
8
+-------------+---------+
| Column Name | Type |
+-------------+---------+
| id | int |
| score | decimal |
+-------------+---------+
在 SQL 中,id 是该表的主键。
该表的每一行都包含了一场比赛的分数。Score 是一个有两位小数点的浮点值。

查询并对分数进行排序。排名按以下规则计算:

  • 分数应按从高到低排列。
  • 如果两个分数相等,那么两个分数的排名应该相同。
  • 在排名相同的分数后,排名数应该是下一个连续的整数。换句话说,排名之间不应该有空缺的数字。

score 降序返回结果表。

CodeDemo

1
2
3
4
5
6
7
8
9
select
score,
rk as `rank`
from (
select
*,
dense_rank() over(order by score desc) as rk
from Scores
) tmp order by `rank`

连续出现的数字

表:Logs

1
2
3
4
5
6
7
+-------------+---------+
| Column Name | Type |
+-------------+---------+
| id | int |
| num | varchar |
+-------------+---------+
id 是这个表的主键。

编写一个 SQL 查询,查找所有至少连续出现三次的数字。

返回的结果表中的数据可以按 任意顺序 排列。

CodeDemo

1
2
3
4
5
6
7
8
9
10
# 使用自连接查询, 查询方式为多个where条件
select
distinct t1.Num as ConsecutiveNums
# 这里如果写count的话在没有数据的测试用例会出现0, 与预期的空不符合,因此写t1.Num并去重比较合理
from Logs t1, Logs t2, Logs t3
where
t1.Num = t2.Num and
t1.Num = t3.Num and
t1.Id + 1 = t2.Id and
t2.Id + 1 = t3.Id

超过经理收入的员工

表:Employee

1
2
3
4
5
6
7
8
9
10
+-------------+---------+
| Column Name | Type |
+-------------+---------+
| id | int |
| name | varchar |
| salary | int |
| managerId | int |
+-------------+---------+
Id是该表的主键。
该表的每一行都表示雇员的ID、姓名、工资和经理的ID。

编写一个SQL查询来查找收入比经理高的员工。

任意顺序 返回结果表。

CodeDemo

1
2
3
4
select 
e1.name as Employee
from Employee e1 join Employee e2 on e1.managerId = e2.id
where e1.salary > e2.salary

查找重复的电子邮箱

案例

表: Person

1
2
3
4
5
6
7
8
+-------------+---------+
| Column Name | Type |
+-------------+---------+
| id | int |
| email | varchar |
+-------------+---------+
id 是该表的主键列。
此表的每一行都包含一封电子邮件。电子邮件不包含大写字母。

编写一个 SQL 查询来报告所有重复的电子邮件。 请注意,可以保证电子邮件字段不为 NULL。

任意顺序 返回结果表。

CodeDemo

1
2
3
4
5
6
7
8
select
email as email
from (
select
email,
count(*) as cnt
from Person group by email
) tmp where cnt > 1;