我有一个表有这个结构
EmployeeID | LogDate | LogTime | TerminalID | InOut | Accepted
此表处理员工的所有出席
InOut Column = 0 - >在(员工刚刚开始他的 移)
Inout Column = 1 - > Out(员工刚刚开始 结束他的转变)
例如,上一张图片的EmployeeID = 1009 在2015-10-14(06:56:28)和(16:13:51)有2拳 我需要在结果中给我他在这两次2次之间参加的时间 这是(09:17:23)
我想要这个结果结构
EmployeeID | LogDate | NumberOfPunshings | State | HoursAttending
我试过这个查询
select
Employeeid as EmpID,
logdate as logdt,
count(accepted) NumberOfPunshings,
case count(accepted) WHEN 1 THEN 'No Out Punch'
WHEN 2 THEN 'Perfect'
Else 'Null'
End as State,
CONVERT(varchar(12),
DATEADD(minute,
DATEDIFF(minute,
(select top 1 LogTime from Accesslog where Inout=0),
(select top 1 LogTime from Accesslog where InOut=1)), 0), 114) as HoursAttending
from Accesslog
where Logdate = CAST('2015-10-14' AS datetime)
group by
employeeid,logdate
order by Employeeid
但它不能正常工作因为我想在HoursAttending中只取一个First值(表)
我创建了SQL小提示,向您展示它看起来如何的数据
http://sqlfiddle.com/#!3/0152f9/1
EmpID | logdt | NumberOfPunshings | State | HoursAttending
1009 | October, 14 2015 00:00:00 | 2 | Perfect | 08:00:00:000
1088 | October, 15 2015 00:00:00 | 2 | Perfect | 08:00:00:000
预期结果必须
EmpID | logdt | NumberOfPunshings | State | HoursAttending
1009 | October, 14 2015 00:00:00 | 2 | Perfect | 08:00:00:000
1088 | October, 15 2015 00:00:00 | 2 | Perfect | 06:00:00:000
这些表格在HoursAttending Column中的差异,因为
第一个员工(1009)从08:00开始工作到16:00所以 持续时间是(08:00)正确。
第二名员工(1088)从009:00到15:00开始工作 持续时间必须是(06:00)而不是(08:00)正确。
答案 0 :(得分:2)
想象一下,如果我们可以轻松获得数据,那将是可能的,并且我们清楚地了解预期的最终结果应该是什么样的。
MS SQL Server 2014架构设置:
CREATE TABLE Accesslog
([EmployeeID] int, [LogDate] datetime, [LogTime] datetime, [Terminal] varchar(11), [InOut] int, [Accepted] int)
;
INSERT INTO Accesslog
([EmployeeID], [LogDate], [LogTime], [Terminal], [InOut], [Accepted])
VALUES
(1009, '2015-10-14 00:00:00', '1900-01-01 06:36:06', 'abcdedghijk', 0, 1),
(1009, '2015-10-14 00:00:00', '1900-01-01 16:22:41', 'abcdedghijk', 1, 1)
;
查询1 :
select
EmployeeID
, LogDate
, MIN(case when InOut = 0 then cast(LogTime as time) end) as LogTimeMin
, MAX(case when InOut = 1 then cast(LogTime as time) end) as LogTimeMax
, COUNT(*) as CountPunches
, CONVERT(varchar(12),
DATEADD(minute,
DATEDIFF(minute,
MIN(case when InOut = 0 then cast(LogTime as time) end),
MAX(case when InOut = 1 then cast(LogTime as time) end)), 0), 114) as HoursAttending
from Accesslog
group by
EmployeeID
, LogDate
<强> Results 强>:
| EmployeeID | LogDate | LogTimeMin | LogTimeMax | CountPunches | HoursAttending |
|------------|------------------|-------------|-------------|--------------|----------------|
| 1009 | October, 14 2015 | 06:36:06.00 | 16:22:41.00 | 2 | 09:46:00:000 |
第2部分
要解决轮班问题,请尝试以下方法。请注意,如果您每天只想要一行,请按查询使用组,但将下面的查询显示为&#34;派生表&#34; (子查询)
MS SQL Server 2014架构设置:
CREATE TABLE Accesslog
([EmployeeID] int, [LogDate] datetime, [LogTime] datetime, [Terminal] varchar(11), [InOut] int, [Accepted] int)
;
INSERT INTO Accesslog
([EmployeeID], [LogDate], [LogTime], [Terminal], [InOut], [Accepted])
VALUES
(1209, '2015-10-14 00:00:00', '1900-01-01 07:00:00', 'abcdedghijk', 0, 1),
(1209, '2015-10-14 00:00:00', '1900-01-01 12:01:00', 'abcdedghijk', 1, 1),
(1209, '2015-10-14 00:00:00', '1900-01-01 15:00:00', 'abcdedghijk', 0, 1),
(1209, '2015-10-14 00:00:00', '1900-01-01 20:02:00', 'abcdedghijk', 1, 1),
(1009, '2015-10-14 00:00:00', '1900-01-01 08:00:00', 'abcdedghijk', 0, 1),
(1009, '2015-10-14 00:00:00', '1900-01-01 16:00:00', 'abcdedghijk', 1, 1),
(1088, '2015-10-15 00:00:00', '1900-01-01 09:00:00', 'aaaa', 0, 1),
(1088, '2015-10-15 00:00:00', '1900-01-01 15:00:00', 'aaaa', 1, 1)
;
查询1 :
/*
including (07:00 - 12:00) shift two (15:00 - 20:00)
*/
WITH CTE as (
SELECT *, ROW_NUMBER() OVER(PARTITION BY EmployeeID, LogDate, InOut
ORDER BY LogTime ASC) AS shiftno
FROM Accesslog
)
SELECT
ins.EmployeeID
, ins.LogDate
, ins.LogTime as LogTimeIn
, outs.LogTime as LogTimeOut
, ins.Accepted + ISNULL(outs.Accepted,0) as CountPunches
, CONVERT(varchar(12),
DATEADD(minute,
DATEDIFF(minute,
ins.LogTime,
outs.LogTime), 0), 114) as HoursAttending
FROM CTE AS ins
INNER JOIN CTE AS outs ON ins.InOut = 0 AND outs.InOut = 1
AND ins.EmployeeID = outs.EmployeeID
AND ins.LogDate = outs.LogDate
AND ins.shiftno = outs.shiftno
<强> Results 强>:
| EmployeeID | LogDate | LogTimeIn | LogTimeOut | CountPunches | HoursAttending |
|------------|---------------------------|---------------------------|---------------------------|--------------|----------------|
| 1009 | October, 14 2015 00:00:00 | January, 01 1900 08:00:00 | January, 01 1900 16:00:00 | 2 | 08:00:00:000 |
| 1088 | October, 15 2015 00:00:00 | January, 01 1900 09:00:00 | January, 01 1900 15:00:00 | 2 | 06:00:00:000 |
| 1209 | October, 14 2015 00:00:00 | January, 01 1900 07:00:00 | January, 01 1900 12:01:00 | 2 | 05:01:00:000 |
| 1209 | October, 14 2015 00:00:00 | January, 01 1900 15:00:00 | January, 01 1900 20:02:00 | 2 | 05:02:00:000 |