Skip to content

Commit 8058083

Browse files
committed
Consecutive Numbers
1 parent 47a11b4 commit 8058083

File tree

4 files changed

+136
-3
lines changed

4 files changed

+136
-3
lines changed

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,7 @@
5353
+ [176 Second Highest Salary (子查询)](database/SecondHighestSalary)
5454
+ [177 Nth Highest Salary(定义函数,变量,分支结构)](database/NthHighestSalary)
5555
+ [178 Rank Scores (导出表、聚集)](database/RankScores)
56+
+ [180 Consecutive Numbers(case语句)](database/ConsecutiveNumbers)
5657
+ [181 Employees Earning More Than Their Managers(自连接)](database/EmployeesEarningMoreThanTheirManagers)
5758
+ [182 Duplicate Emails(分组过滤)](database/DuplicateEmails)
5859
+ [183 Customers Who Never Order(exists子句)](database/CustomersWhoNeverOrder)

database/ConsecutiveNumbers/README.md

Lines changed: 65 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,65 @@
1+
## Consecutive Numbers
2+
3+
Write a SQL query to find all numbers that appear at least three times consecutively.
4+
```
5+
+----+-----+
6+
| Id | Num |
7+
+----+-----+
8+
| 1 | 1 |
9+
| 2 | 1 |
10+
| 3 | 1 |
11+
| 4 | 2 |
12+
| 5 | 1 |
13+
| 6 | 2 |
14+
| 7 | 2 |
15+
+----+-----+
16+
```
17+
For example, given the above Logs table, 1 is the only number that appears consecutively for at least three times.
18+
19+
## Solution 1
20+
21+
使用自连接,然后一一和上一个比较,最后分组过滤即可
22+
```sql
23+
select log1.Num from Logs log1 join Logs log2 on log1.Id + 1 = log2.Id and log1.Num = log2.Num group by log1.Num having count(log1.Num) >= 2;
24+
```
25+
26+
结果超时, 可能是分组导致的。
27+
28+
## Solution 2
29+
30+
还是使用自连接,不过为了避免group开销,直接使用三个表连接,分别指向Id, Id + 1, Id + 2,并分别让Num相等即可
31+
32+
```sql
33+
select distinct a.Num from Logs a, Logs b,Logs c where a.Id=b.Id+1 and a.Num=b.Num and b.Id=c.Id+1 and b.Num=c.Num;
34+
```
35+
36+
## Solution 3
37+
38+
统计法。如果这一题使用c编程实现,逐行读取,这就容易了。
39+
40+
可以使用case语句实现:
41+
```sql
42+
select Num from (
43+
SELECT
44+
Num,
45+
CASE
46+
WHEN @prevNum = Num THEN @count := @count + 1
47+
WHEN @prevNum := Num THEN @count := 1
48+
END n
49+
FROM Logs, (select @prevNum := NULL) initPrevNum, (select @count := 1) initCount
50+
) as result where result.n >= 3;
51+
```
52+
注意在case后的结果别名为n,当不能直接在该语句中使用,必须使用另一个select语句查询。
53+
`when`是一个短路的,相当于`if``:=`用于赋值,`=`用于比较,必须在`from`语句中初始化`prevNum, count`的值
54+
55+
## mysql case 语句
56+
57+
相当于switch语句,when后面结条件,并且是短路的。例子:
58+
```sql
59+
select Num,
60+
case
61+
when Num % 2 = 0 then "Even"
62+
when Num % 2 = 1 then "Odd"
63+
end Numtype
64+
from Logs;
65+
```
Lines changed: 41 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,49 @@
11
use leetcode;
2-
create table if not exists Logs(Id int, Num int);
3-
/*
2+
drop table if exists Logs;
3+
create table Logs(Id int, Num int);
44
insert into Logs values(1,1);
55
insert into Logs values(2,1);
66
insert into Logs values(3,1);
77
insert into Logs values(4,2);
88
insert into Logs values(5,1);
99
insert into Logs values(6,2);
1010
insert into Logs values(7,2);
11-
*/
11+
insert into Logs values(8,2);
12+
insert into Logs values(9,1);
13+
insert into Logs values(10,1);
14+
insert into Logs values(11,1);
15+
insert into Logs values(12,3);
16+
insert into Logs values(13,3);
17+
insert into Logs values(14,3);
18+
insert into Logs values(15,4);
19+
insert into Logs values(16,4);
20+
insert into Logs values(17,5);
21+
insert into Logs values(18,5);
22+
23+
select "Method 1";
24+
select log1.Num from Logs log1 join Logs log2 on log1.Id + 1 = log2.Id and log1.Num = log2.Num group by log1.Num having count(log1.Num) >= 2;
25+
26+
select "Method 2";
27+
select distinct a.Num from Logs a, Logs b,Logs c where a.Id=b.Id+1 and a.Num=b.Num and b.Id=c.Id+1 and b.Num=c.Num;
28+
29+
select "Method 3";
30+
SELECT DISTINCT `Num` FROM (
31+
SELECT
32+
`Num`,
33+
CASE
34+
WHEN @prevNum = `Num` THEN @count := @count + 1
35+
WHEN (@prevNum := `Num`) IS NOT NULL THEN @count := 1
36+
END n
37+
FROM `Logs`, (SELECT @prevNum := NULL) r, (SELECT @count := 1) c
38+
) a WHERE n >= 3;
39+
40+
select "Method 4";
41+
SELECT DISTINCT `Num` FROM (
42+
SELECT
43+
`Num`,
44+
CASE
45+
WHEN @prevNum = `Num` THEN @count := @count + 1
46+
WHEN (@prevNum := `Num`) IS NOT NULL THEN @count := 1
47+
END n
48+
FROM `Logs`
49+
) a WHERE n >= 3;

database/ConsecutiveNumbers/when.sql

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
use leetcode;
2+
select Num,
3+
case
4+
when Num % 2 = 0 then "Even"
5+
when Num % 2 = 1 then "Odd"
6+
end Numtype
7+
from Logs;
8+
9+
select Num from (
10+
SELECT
11+
Num,
12+
CASE
13+
WHEN @prevNum = Num THEN @count := @count + 1
14+
WHEN @prevNum := Num THEN @count := 1
15+
END n
16+
FROM Logs, (select @prevNum := NULL) initPrevNum, (select @count := 1) initCount
17+
) as result where result.n >= 3;
18+
/*
19+
SELECT * FROM (
20+
SELECT
21+
`Num`,
22+
CASE
23+
WHEN @prevNum = `Num` THEN @count := @count + 1
24+
WHEN @prevNum := `Num` THEN @count := 1
25+
END n
26+
FROM `Logs`, (select @prevNum := NULL) r, (select @count := 1) s
27+
) a;
28+
29+
*/

0 commit comments

Comments
 (0)