【问题标题】:Calculate overtime per day计算每天的加班时间
【发布时间】:2013-07-16 14:40:19
【问题描述】:

我有一个 sql 代码,可以获取每个员工的总工作时间和他的超时时间。我想计算他当天工作的总加班时间。你能帮我解决这个问题吗? 8 小时是每天的固定时间。

这是代码

SELECT
  empno,
  date_created,
  time_in,
  time_out,
  time_format(timediff(time_out, time_in), '%H:%i') AS total_time
FROM
(
  SELECT empno, date_created,
    min(CASE WHEN status = 0 THEN time_created END) time_in,
    max(CASE WHEN status = 1 THEN time_created END) time_out
  FROM biometrics
  WHERE empno = 3
  GROUP BY empno, date_created
) t1;

样本输出

empno| date_created | time_in | time_out
  2      2013-07-15   11:08:07  15:00:00
  3      2013-07-15   11:50:00  NULL
  4      2013-07-15    NULL     16:00:00

我想要的是这样的

empno | date_created | time_in | time_out | overtime
 2       2013-07-15    5:00:00  15:00:00      2

【问题讨论】:

    标签: mysql sql


    【解决方案1】:

    你可以这样做

    SELECT empno, date_created, time_in, time_out, 
           CASE WHEN total_hours - 8 > 0 THEN total_hours - 8 ELSE 0 END overtime
      FROM
    (
      SELECT empno, date_created, time_in, time_out,
             TIME_TO_SEC(TIMEDIFF(COALESCE(time_out, '17:00:00'),
                                  COALESCE(time_in,  '09:00:00'))) / 3600 total_hours
        FROM
      (
        SELECT empno, date_created, 
               MIN(CASE WHEN status = 0 THEN time_created END) time_in,
               MIN(CASE WHEN status = 1 THEN time_created END) time_out
          FROM biometrics
         GROUP BY empno, date_created
      ) a
    ) b
    

    这里是SQLFiddle演示

    您需要为time_intime_out 提供真正的默认值,以用于NULL 的情况。在极端情况下,如果 NULLs 是由于员工前一天来和回家这一事实引起的,那么这些默认值可能分别为 00:00:0023:59:59,因为您正在计算每个日历日的加班时间。

    更新:如果您希望overtime 以时间格式显示

    SELECT empno, date_created, time_in, time_out, 
           SEC_TO_TIME(
             CASE WHEN total_sec - 28800 > 0 
                  THEN total_sec - 28800 
                  ELSE 0 END) overtime
      FROM
    (
      SELECT empno, date_created, time_in, time_out,
             TIME_TO_SEC(TIMEDIFF(COALESCE(time_out, '17:00:00'),
                                  COALESCE(time_in,  '09:00:00'))) total_sec
        FROM
      (
        SELECT empno, date_created, 
               MIN(CASE WHEN status = 0 THEN time_created END) time_in,
               MIN(CASE WHEN status = 1 THEN time_created END) time_out
          FROM biometrics
         GROUP BY empno, date_created
      ) a
    ) b
    

    这里是SQLFiddle演示

    【讨论】:

    • 哦!不知道我该怎么感谢你。谢谢你正是我要找的。我一直在网上搜索这个。 @peterm
    【解决方案2】:
    SELECT IFNULL(TIMEDIFF('08:00:00',(TIMEDIFF(time_out,time_in))),0) 
    AS OVERTIME
    FROM biometrics
    

    【讨论】:

      猜你喜欢
      • 2022-10-24
      • 1970-01-01
      • 2016-10-16
      • 2019-02-13
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-01-04
      • 1970-01-01
      相关资源
      最近更新 更多