1

我有一个按以下顺序存储时钟条目的表。

UID         Clock                    Status
===         =====                    ======

R01         2013-01-01 17:00:00      Clockin
R01         2013-01-01 17:10:00      Clockin
R01         2013-01-01 23:45:00      Clockin

我目前的解决方案是使用 Min/Max date with case and left join 按以下顺序排列条目

UID        Date         ClockIn    ClockOut
===        ====         =======    ========
R01        2013-01-01    17:00:00  23:45:00

当时钟输入跨越午夜时,我应该如何处理这种情况。IE,

UID         Clock                    Status
===         =====                    ======
R01         2013-01-01 17:00:00      Clockin
R01         2013-01-02 00:45:00      Clockin

由于上述将产生 2 个如下条目,这将导致员工的零时间状态为 7.45 小时。

UID        Date          ClockIn               ClockOut
===        ====          =======               ========
R01        2013-01-01    2013-01-01 17:00:00   2013-01-01 17:00:00
R01        2013-01-02    2013-01-02 00:45:00   2013-01-02 00:45:00

提前致谢。

这是 SQL 2008R2 中使用的存储过程的代码

SELECT A.Device,A.DID, A.Name, A.ClockDate,Clockin ,ClockOut
FROM 
(
    SELECT Device,DID,Name, CONVERT(DATE, DeviceClock) 'ClockDate', 
    min(case when clock=Clock and Status ='Clock In' OR status='Clock Out' OR status='Access In' then clock  end) 'CLock In'

    FROM TABLE  
    group by Device,DID,Name, CONVERT(DATE, DeviceClock)
) as A
LEFT JOIN 
(
    SELECT Device,DID,Name, CONVERT(DATE, DeviceClock) 'ClockDate', 

max(case when clock=Clock and Status ='Clock in' or status='Clock Out' OR status='Access In' then Clock end) 'Clock Out'


    FROM TABLE 
    group by Device,DID,Name, CONVERT(DATE, DeviceClock)
) as B
ON A.DID = B.DID AND A.ClockDate = B.ClockDate
4

2 回答 2

2

这里有很多你没有考虑到的。时间/考勤系统非常复杂。例如:

  • 如果您的 ClockIn 仅在午夜前几分钟,而 ClockOut 则在早上很晚怎么办?你把时间记录到哪一天?
  • 如果时间平均分配,比如晚上 10 点到凌晨 2 点,那会是第 1 天的一个 4 小时轮班吗?还是第 2 天?或者是两个 2 小时的轮班?
  • 你用UTC记录时间吗?进行本地转换?处理夏令时?(在本地时间减去减去不是对经过持续时间的准确测量!)
  • 四舍五入?多少?在什么场景下?
  • 如何处理丢失的拳头?重复拳?

有整个系统已经发展到可以处理这些场景。他们通常还处理工作规则,如加班计算、工作成本计算、日程安排和其他事情——但他们都从你描述的基本问题案例开始。

您并不总是与下一拳配对,或特定类型的下一拳,或同一日期的下一拳。有多种场景组合需要处理,你无法用简单的 sql 语句或存储过程来表达。您可以尝试- 但您将有很多边缘情况需要处理。

我会考虑购买已经为您处理这些案例的产品。如果您打算自己编写 - 不要在 SQL 中编写。从 SQL 中获取原始数据并将其与您的业务逻辑一起使用以生成处理引擎。

于 2012-12-31T18:04:35.947 回答
1

马特所说的是一个很好的一般性答案,并阅读了他提到的所有警告,但如果你的情况很简单,所有员工在早上 6 点之后开始,在午夜之前离开并在比如说凌晨 3 点之前完成,你可以很好地捏造它这个:

SELECT Device,DID,Name, convert( DATE, dateadd(hour, -3, CONVERT(DATE, DeviceClock))) 'ClockDate', 

max(case when clock=Clock and Status ='Clock in' or status='Clock Out' OR status='Access In' then Clock end) 'Clock Out'

FROM TABLE 
group by Device,DID,Name, convert( DATE, dateadd(hour, -3, CONVERT(DATE, DeviceClock)))

在两个加入的选择中的每一个中。你有效地将一天的开始和结束时间缩短了 3 个小时。当然,如果有人在凌晨 3 点以后工作,或者在凌晨 3 点之前开始工作,这将不起作用。

于 2012-12-31T18:23:56.107 回答