Leetcode - 579. Find Cumulative Salary of an Employee

The Employee table holds the salary information in a year.

Write a SQL to get the cumulative sum of an employee's salary over a period of 3 months but exclude the most recent month.

The result should be displayed by 'Id' ascending, and then by 'Month' descending.

Example
Input

| Id | Month | Salary |
|----|-------|--------|
| 1  | 1     | 20     |
| 2  | 1     | 20     |
| 1  | 2     | 30     |
| 2  | 2     | 30     |
| 3  | 2     | 40     |
| 1  | 3     | 40     |
| 3  | 3     | 60     |
| 1  | 4     | 60     |
| 3  | 4     | 70     |

Output

| Id | Month | Salary |
|----|-------|--------|
| 1  | 3     | 90     |
| 1  | 2     | 50     |
| 1  | 1     | 20     |
| 2  | 1     | 20     |
| 3  | 3     | 100    |
| 3  | 2     | 40     |

Employee '1' has 3 salary records for the following 3 months except the most recent month '4': salary 40 for month '3', 30 for month '2' and 20 for month '1'
So the cumulative sum of salary of this employee over 3 months is 90(40+30+20), 50(30+20) and 20 respectively.

| Id | Month | Salary |
|----|-------|--------|
| 1  | 3     | 90     |
| 1  | 2     | 50     |
| 1  | 1     | 20     |

Employee '2' only has one salary record (month '1') except its most recent month '2'.

| Id | Month | Salary |
|----|-------|--------|
| 2  | 1     | 20     |

Employ '3' has two salary records except its most recent pay month '4': month '3' with 60 and month '2' with 40. So the cumulative salary is as following.

| Id | Month | Salary |
|----|-------|--------|
| 3  | 3     | 100    |
| 3  | 2     | 40     |


Make clear: get the cumulative sum of an employee's salary over a period of 3 months 是指每个月都计算与其相邻的三个月的总和,如果不满三个月则计算全部的总和。

思路:

1. 首先exclude the most recent month

select e1.Id, e1.Month, e1.Salary
from Employee e1, 
(select Id, max(Month) as max_month
from Employee
group by Id
order by Month desc) e2
where e1.Id = e2.Id
and e1.Month != e2.max_month

得到table如下:

IdMonthSalary
1120
2120
1230
3240
1340
3360

2. 通过self join on a.Id = b.Id and a.Month >= b.Month 得到table如下:

Id1Month1Salary1Id2Month2Salary2
11201120
12301120
12301230
13401120
13401230
13401340
21202120
32403240
33603240
33603360

可以看到,如果group by id1 and Month1的话,sum(Salary2)则为cumulative salary。但要注意的是,只cumulative相邻的三个月,即Month1和Month2的差值应小于3.

coding 如下:

select a.Id as id, a.Month as month, sum(b.Salary) as Salary
from 

(select e1.Id, e1.Month, e1.Salary
from Employee e1, 
(select Id, max(Month) as max_month
from Employee
group by Id
order by Month desc) e2
where e1.Id = e2.Id
and e1.Month != e2.max_month) a,

(select e1.Id, e1.Month, e1.Salary
from Employee e1, 
(select Id, max(Month) as max_month
from Employee
group by Id
order by Month desc) e2
where e1.Id = e2.Id
and e1.Month != e2.max_month) b

where a.Id = b.Id
and a.Month >= b.Month
and a.Month - b.Month < 3
group by a.Id, a.Month
order by a.Id, a.Month desc

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值