检查计划中是否重叠

时间:2015-08-04 18:18:03

标签: sql sql-server-2008

我有一张列出员工日程表的表格。我需要编写一个查询来确定是否有多个人同时处理同一个任务。我的数据如下:

EmployeeID  JobID   StartTime   EndTime     M   Tu  W   Th  F   Sa  Su
======================================================================
10001       201     12:00:00    14:00:00    1   1   1   1   1   0   0
10001       202     15:00:00    17:00:00    1   1   1   1   1   0   0
10001       202     17:30:00    18:30:00    1   1   1   1   1   0   0
10002       202     16:00:00    18:00:00    1   1   1   1   1   0   0

我正在尝试的要点如下,但显然这是不正确的。我只是无法弄清楚在哪里开始寻找解决这个问题的方法。

select * 
from Table1 
where (JobID=JobID) AND 
    (StartTime > StartTime AND StartTime < EndTime) OR
    (EndTime > StartTime AND EndTime < EndTime)

我确实需要考虑几天,但是一旦我弄清楚如何进行查询的其余部分,这应该是非常直接的。

4 个答案:

答案 0 :(得分:0)

你很近但你需要两次引用同一张桌子。因此,您需要JOIN来表示重叠表。尝试这样的事情:

SELECT * 
FROM Table1 AS t1
JOIN Table1 AS t1_overlap ON
    t1_overlap.JobID = t1.JobID
    AND t1_overlap.EmployeeID != t1.EmployeeID
    AND (t1_overlap.StartTime BETWEEN  t1.StartTime AND t1.EndTime
        OR t1_overlap.EndTime BETWEEN  t1.StartTime AND t1.EndTime)
    AND t1_overlap.M = t1.M
    AND t1_overlap.Tu = t1.Tu
    AND t1_overlap.W = t1.W
    AND t1_overlap.Th = t1.Th
    AND t1_overlap.F = t1.F
    AND t1_overlap.Sa = t1.Sa
    AND t1_overlap.Su = t1.Su

答案 1 :(得分:0)

执行此操作的一种快速方法是使用自联接,因为您需要比较具有相同JobID的同一个表中的多个行。试试这个:

select t1.*
from table1 t1
inner join table1 t2 on t1.JobID = t2.JobID
where (
    t1.StartTime BETWEEN t2.StartTime and t2.EndTime
    or t1.EndTime BETWEEN t2.StartTime and t2.EndTime
)

如果使用窗口函数,也可以更有效地执行此操作,但它们更高级,因此上述内容是实现所需内容的直接方法。

答案 2 :(得分:0)

您只需像其他人提到的那样在同一张桌子上self join,并确保加入以下条件:

SELECT distinct
     t1.EmployeeID as FirstEmployee,
     t2.EmployeeID as SecondEmployee,
     t1.StartTime as FirstEmployeeStartTime,
     t2.StartTime as SecondEmployeeStartTime,         
     t1.EndTime as FirstEmployeeEndTime,
     t2.EndTime as SecondEmployeeEndTime
FROM table1 t1
INNER JOIN table1 t2 ON t1.JobID = t2.JobID
    AND t1.employeeid <> t2.employeeid
    AND (
        t1.StartTime BETWEEN t2.StartTime
            AND t2.EndTime
        OR t1.EndTime BETWEEN t2.StartTime
            AND t2.EndTime
        )

toobusy-js

答案 3 :(得分:0)

所以,你已经知道你需要一个自我加入,因为所有其他答案都告诉你。但是,我没有看到任何当前的答案测试重叠正确的方式。

如果(并且仅当)第一个开始小于第二个开始时,任何2个范围重叠,而第二个开始小于第一个开始。 因此,如果表的其他记录以及结束日期与表中其他记录的开始日期相比,您希望根据结束日期测试开始日期。

查看wiki中的H标记,了解我的意思。