【发布时间】:2021-05-02 02:28:44
【问题描述】:
我在 SQL Server 中有一个这样的表:
+----------+-----------+------------+
| DateFrom | Completed | EmployeeID |
+----------+-----------+------------+
DateFrom: date not null -- unique for each EmployeeID
Completed: bit not null
EmployeeID: bigint not null
- 每一行都属于一个由开始日期定义的子期间,可以完成也可以不完成。
- 每个员工可以有多个子期间。
- 期间由有序子期间列表定义,直到最后一个子期间完成。
我想创建一个视图,该视图将返回每个 EmployeeID 的最后一个期间的开始日期,如下所示:
- 如果没有 Completed 为 true,则获取最小 DateFrom。 [员工有一个时期尚未完成]
+----------+-----------+------------+
| DateFrom | Completed | EmployeeID |
+----------+-----------+------------+
|2021-01-01| false | 1 |
|2021-01-05| false | 1 |
|2021-01-09| false | 1 |
|2021-01-10| false | 1 |
|2021-01-07| false | 2 |
|2021-01-15| false | 2 |
+----------+-----------+------------+
Expected Result:
2021-01-01 for EmployeeID = 1
2021-01-07 for EmployeeID = 2
- 否则,返回最后一个 Completed 为 true 后的最小 DateFrom。 [最后一期还没有完成]
+----------+-----------+------------+
| DateFrom | Completed | EmployeeID |
+----------+-----------+------------+
|2021-01-01| false | 1 |
|2021-01-05| true | 1 |
|2021-01-09| false | 1 |
|2021-01-10| false | 1 |
|2021-01-07| true | 2 |
|2021-01-15| false | 2 |
+----------+-----------+------------+
Expected Result:
2021-01-09 for EmployeeID = 1
2021-01-15 for EmployeeID = 2
- 如果最大 DateFrom 已 Completed=true,则返回最后一个 Completed 为 true 之前的最小 DateFrom,如果存在,则返回它之前的 true。 [最后一期完成,有多个子期]
+----------+-----------+------------+
| DateFrom | Completed | EmployeeID |
+----------+-----------+------------+
|2021-01-01| false | 1 |
|2021-01-05| true | 1 |
|2021-01-09| false | 1 |
|2021-01-10| true | 1 |
|2021-01-07| false | 2 |
|2021-01-15| true | 2 |
+----------+-----------+------------+
Expected Result:
2021-01-09 for EmployeeID = 1
2021-01-07 for EmployeeID = 2
- 如果最大 DateFrom 的 Completed=true 并且没有其他行或之前的行 Completed=true,则返回最大 DateFrom。 [最后一期以一个子期结束]
+----------+-----------+------------+
| DateFrom | Completed | EmployeeID |
+----------+-----------+------------+
|2021-01-01| false | 1 |
|2021-01-05| false | 1 |
|2021-01-09| true | 1 |
|2021-01-10| true | 1 |
|2021-01-07| true | 2 |
+----------+-----------+------------+
Expected Result:
2021-01-10 for EmployeeID = 1
2021-01-07 for EmployeeID = 2
我正在寻找最优化的解决方案。
我试过了,但在第三个例子中我得到了一个 NULL 值:
WITH T AS (
SELECT EmployeeID
, MAX(CASE WHEN Completed = 0 THEN NULL ELSE DateFrom END) MaxDateFrom
FROM TableDates
GROUP BY EmployeeID
)
SELECT TableDates.EmployeeID, MIN(TableDates.DateFrom) DateFrom
FROM T
LEFT JOIN TableDates ON T.EmployeeID = TableDates.EmployeeID
AND (T.MaxDateFrom IS NULL OR TableDates.DateFrom > T.MaxDateFrom)
GROUP BY TableDates.EmployeeID
【问题讨论】:
标签: sql sql-server tsql view minimum