我的数据包含不同行的重叠日期。对于包含重叠的每两行,我需要按照以下方式对其进行适当的分解。
首先,数据如下所示:
EMPID FIRSTNAME SURNAME ACTIVITY START_DATE END_DATE HOURS_PER_DAY STATION
101 ANDREW SMITH AVAILABLE 2013-07-08 09:00:00 2013-07-08 17:00:00 8.00 LONDON
101 ANDREW SMITH SICKNESS 2013-07-08 07:00:00 2013-07-08 12:00:00 5.00 LONDON
原因是数据最初来自两个独立的表,我已将两个表的内容插入一个。
此数据最终将按人数分组,提供“每日小时数”列。在上表中,这个人将有13个小时,但正如我们在上面所看到的,两个时期的时间跨度只有10个小时。
在上面的例子中,我需要将结果分成3行 - 重叠前的位,重叠和重叠后的位:
EMPID NAME ACTIVITY START_DATE END_DATE HOURS_PER_DAY STATION
101 JOHN SICKNESS 2013-07-08 07:00:00 2013-07-08 09:00:00 2 LONDON
101 JOHN SICKNESS 2013-07-08 09:00:00 2013-07-08 12:00:00 3 LONDON
101 JOHN AVAILABLE 2013-07-08 12:00:00 2013-07-08 17:00:00 5 LONDON
对于重叠的时间段必须归类为疾病。请注意除了可用和疾病之外还有其他选择,但唯一重叠的是疾病与任何其他类型,例如'疾病'和'可用'之间的冲突或'疾病'和'训练'之间的冲突。
此外,数据已被分为24小时 - 即我已经将4天内的疾病期推断为4个不同的行,这就是为什么每天的小时数列永远不会超过24小时 - 如果满了如果存在24小时,则结束日期将在开始日期后的1天内完成 - 开始日期和结束日期均为午夜。当我尝试执行所需的操作时,我尝试按EMPID,NAME,CAST(START_DATE)AS DATE,CAST(END_DATE AS DATE)和STATION对数据进行分组。这些是确定需要比较的分组的适当字段。
请注意目前约有。 2500行数据与提供的数据相似,并且可能存在以下类型的重叠(如果AVAILABLE条目从09:00开始并在17:00结束 - 请注意,我不是仅仅使用它作为示例:
请再次注意'AVAILABLE'不是唯一的选择。
我的查询目前正在以这篇文章顶部的格式返回数据,该格式存储在临时表@INDIVIDUALDAYS中 - 我现在想做@INDIVIDUALDAYS所需的任何内容来将其外推为描述上方。
我希望以完全相同的格式返回相同列的数据(只需外推到多行,因为我需要对它进行一些进一步的操作和计算。
如果需要,我很乐意提供我当前的代码,但它超过200行,我相信我已经给了你足够的信息
以下是一些涵盖上述7种不同渗透的样本数据:
101 Andrew Smith Available 2014-08-19 09:00:00.000 2014-08-19 17:00:00.000 8.00 London
101 Andrew Smith SICKNESS 2014-08-19 09:00:00.000 2014-08-19 17:00:00.000 8.00 London
101 Andrew Smith SICKNESS 2014-08-20 12:00:00.000 2014-08-20 19:00:00.000 7.00 London
101 Andrew Smith Available 2014-08-20 09:00:00.000 2014-08-20 17:00:00.000 8.00 London
101 Andrew Smith Available 2014-08-21 09:00:00.000 2014-08-21 17:00:00.000 8.00 London
101 Andrew Smith SICKNESS 2014-08-21 04:00:00.000 2014-08-21 12:00:00.000 8.00 London
101 Andrew Smith SICKNESS 2014-08-22 06:00:00.000 2014-08-22 18:00:00.000 12.00 London
101 Andrew Smith Available 2014-08-22 09:00:00.000 2014-08-22 17:00:00.000 8.00 London
101 Andrew Smith Available 2014-08-23 09:00:00.000 2014-08-23 17:00:00.000 8.00 London
101 Andrew Smith SICKNESS 2014-08-23 11:00:00.000 2014-08-23 14:00:00.000 3.00 London
101 Andrew Smith Available 2014-08-24 09:00:00.000 2014-08-23 17:00:00.000 8.00 London
101 Andrew Smith SICKNESS 2014-08-24 09:00:00.000 2014-08-23 14:00:00.000 3.00 London
101 Andrew Smith Available 2014-08-25 09:00:00.000 2014-08-23 17:00:00.000 8.00 London
101 Andrew Smith SICKNESS 2014-08-25 11:00:00.000 2014-08-23 17:00:00.000 3.00 London
答案 0 :(得分:0)
要做到这一点,首先需要将两行组合在一起作为1行。将所有数据作为单行存储后,可以执行一系列联合查询来构建结果行,每个条件都有一个查询。
这会构建测试数据:
INSERT INTO TData
([ID], [FName], [LName], [Status], [StartTime], [EndTime], [Hours], [Location])
VALUES
(101, 'Andrew', 'Smith', 'Available', '2014-08-19 09:00:00', '2014-08-19 17:00:00', 8.00, 'London'),
(101, 'Andrew', 'Smith', 'SICKNESS', '2014-08-19 09:00:00', '2014-08-19 17:00:00', 8.00, 'London'),
(101, 'Andrew', 'Smith', 'SICKNESS', '2014-08-20 12:00:00', '2014-08-20 19:00:00', 7.00, 'London'),
(101, 'Andrew', 'Smith', 'Available', '2014-08-20 09:00:00', '2014-08-20 17:00:00', 8.00, 'London'),
(101, 'Andrew', 'Smith', 'Available', '2014-08-21 09:00:00', '2014-08-21 17:00:00', 8.00, 'London'),
(101, 'Andrew', 'Smith', 'SICKNESS', '2014-08-21 04:00:00', '2014-08-21 12:00:00', 8.00, 'London'),
(101, 'Andrew', 'Smith', 'SICKNESS', '2014-08-22 06:00:00', '2014-08-22 18:00:00', 12.00, 'London'),
(101, 'Andrew', 'Smith', 'Available', '2014-08-22 09:00:00', '2014-08-22 17:00:00', 8.00, 'London'),
(101, 'Andrew', 'Smith', 'Available', '2014-08-23 09:00:00', '2014-08-23 17:00:00', 8.00, 'London'),
(101, 'Andrew', 'Smith', 'SICKNESS', '2014-08-23 11:00:00', '2014-08-23 14:00:00', 3.00, 'London'),
(101, 'Andrew', 'Smith', 'Available', '2014-08-24 09:00:00', '2014-08-23 17:00:00', 8.00, 'London'),
(101, 'Andrew', 'Smith', 'SICKNESS', '2014-08-24 09:00:00', '2014-08-23 14:00:00', 3.00, 'London'),
(101, 'Andrew', 'Smith', 'Available', '2014-08-25 09:00:00', '2014-08-23 17:00:00', 8.00, 'London'),
(101, 'Andrew', 'Smith', 'SICKNESS', '2014-08-25 11:00:00', '2014-08-23 17:00:00', 3.00, 'London')
;
这是结果的开始。您需要为最终显示的每个行/条件添加更多UNION子句。
;WITH Combined AS (
SELECT T1.*, t2.StartTime AS S_StartTime, t2.EndTime AS S_EndTime,
t2.Status AS S_Status, t2.Hours AS S_Hours
FROM TData T1 --Change TData to your table name
LEFT OUTER JOIN Tdata T2 ON T1.id = T2.id
AND CAST(T1.StartTime AS date) = CAST(T2.StartTime as date)
AND t1.Status <> t2.Status
WHERE T1.Status <> 'SICKNESS'
)
--this is case 1 Show sickness only? If not, add another row
SELECT ID, FName, LName, s_Status AS Status,
s_StartTime AS StartTime, s_EndTime AS EndTime,
S_Hours AS Hours, Location
FROM combined
WHERE StartTime = S_StartTime and EndTime = s_EndTime
UNION --Case 2 Row 1
SELECT ID, FName, LName, s_Status AS Status,
s_StartTime AS StartTime, StartTime AS EndTime,
DATEDIFF(minute,S_StartTime,StartTime)/60 AS Hours, Location
FROM combined
WHERE S_StartTime < StartTime
AND S_EndTime BETWEEN StartTime AND EndTime
UNION --case 2 row 2
SELECT ID, FName, LName, S_Status AS Status,
StartTime AS StartTime, S_EndTime AS EndTime,
DATEDIFF(minute,StartTime,S_EndTime)/60 AS Hours, Location
FROM combined
WHERE S_StartTime < StartTime
AND S_EndTime BETWEEN StartTime AND EndTime
UNION --case 2 row 3
SELECT ID, FName, LName, Status,
S_EndTime AS StartTime, EndTime AS EndTime,
DATEDIFF(minute,S_EndTime,EndTime)/60 AS Hours, Location
FROM combined
WHERE S_StartTime < StartTime
AND S_EndTime BETWEEN StartTime AND EndTime
我可以解决其余的条款,但应该很清楚如何做到这一点。如果您需要其他帮助,请与我们联系。