• 根据上班时间、周末、节假日计算两个时间之间的工时


    需求:计算两个时间之间的工作时间,比如:

    计算两个时间的时间差,但是中间有部分时间是要去掉的,比如计算2023-09-10 10:00:00 和 2023-09-15 16:00:00 的时间差,但是要刨除掉17:30~08:30和11:00~13:00的时间,因为这两个时间不是工作时间,同时如果2023-09-10~2023-09-15之间有周末、节假日也要剔除,最终算出来的时长应该是34小时

    代码如下:

    1. import java.time.DayOfWeek;
    2. import java.time.LocalDate;
    3. import java.time.LocalDateTime;
    4. import java.time.LocalTime;
    5. import java.time.format.DateTimeFormatter;
    6. import java.util.ArrayList;
    7. import java.util.List;
    8. public class TimeWorkingHoursCalculator {
    9. private static final DateTimeFormatter TIME_FORMAT = DateTimeFormatter.ofPattern("HH:mm");
    10. private static final DateTimeFormatter DATE_FORMAT = DateTimeFormatter.ofPattern("yyyy-MM-dd");
    11. private LocalTime morningStartTime;
    12. private LocalTime morningEndTime;
    13. private LocalTime afternoonStartTime;
    14. private LocalTime afternoonEndTime;
    15. private List specialRestDays ;
    16. public static void main(String[] args) {
    17. // 设置工作时间段
    18. LocalTime morningStartTime = LocalTime.parse("08:30", TIME_FORMAT);
    19. LocalTime morningEndTime = LocalTime.parse("11:30", TIME_FORMAT);
    20. LocalTime afternoonStartTime = LocalTime.parse("13:00", TIME_FORMAT);
    21. LocalTime afternoonEndTime = LocalTime.parse("17:00", TIME_FORMAT);
    22. // 创建工作时间计算器
    23. TimeWorkingHoursCalculator calculator = new TimeWorkingHoursCalculator(morningStartTime, morningEndTime,
    24. afternoonStartTime, afternoonEndTime);
    25. // 设置特殊休息日
    26. LocalDate specialRestDay1 = LocalDate.parse("2023-07-01", DATE_FORMAT);
    27. LocalDate specialRestDay2 = LocalDate.parse("2023-09-12", DATE_FORMAT);
    28. calculator.addSpecialRestDay(specialRestDay1);
    29. calculator.addSpecialRestDay(specialRestDay2);
    30. // 计算工作小时数
    31. LocalDateTime startTime = LocalDateTime.parse("2023-09-11T10:00", DateTimeFormatter.ISO_LOCAL_DATE_TIME);
    32. LocalDateTime endTime = LocalDateTime.parse("2023-09-15T16:00", DateTimeFormatter.ISO_LOCAL_DATE_TIME);
    33. double workingHours = calculator.calculateWorkingHours(startTime, endTime);
    34. System.out.println("工作小时数:" + workingHours);
    35. }
    36. public TimeWorkingHoursCalculator(LocalTime morningStartTime, LocalTime morningEndTime,
    37. LocalTime afternoonStartTime, LocalTime afternoonEndTime) {
    38. this.morningStartTime = morningStartTime;
    39. this.morningEndTime = morningEndTime;
    40. this.afternoonStartTime = afternoonStartTime;
    41. this.afternoonEndTime = afternoonEndTime;
    42. this.specialRestDays = new ArrayList<>();
    43. }
    44. public void addSpecialRestDay(LocalDate date) {
    45. specialRestDays.add(date);
    46. }
    47. public double calculateWorkingHours(LocalDateTime startTime, LocalDateTime endTime) {
    48. double totalHours = 0.0;
    49. LocalDateTime currentDateTime = startTime;
    50. while (currentDateTime.isBefore(endTime) || currentDateTime.compareTo(endTime) == 0) {
    51. LocalDate currentDate = currentDateTime.toLocalDate();
    52. if (!isWeekend(currentDate) && !isSpecialRestDay(currentDate)) {
    53. LocalTime currentTime = currentDateTime.toLocalTime();
    54. boolean isMorningWorkingHour = currentTime.isAfter(morningStartTime)
    55. && (currentTime.isBefore(morningEndTime) || currentTime.compareTo(morningEndTime) == 0)
    56. && currentDateTime.compareTo(startTime)!=0;//当开始时间为08:30(工作开始时间)时,会导致多出半小时,所以需要增加这个判断
    57. boolean isAfternoonWorkingHour = currentTime.isAfter(afternoonStartTime)
    58. && (currentTime.isBefore(afternoonEndTime) || currentTime.compareTo(afternoonEndTime) == 0 )
    59. && currentDateTime.compareTo(startTime)!=0;
    60. // boolean isMorningWorkingHour = currentTime.isAfter(morningStartTime)
    61. // boolean isAfternoonWorkingHour = currentTime.isAfter(afternoonStartTime) && currentTime.isBefore(afternoonEndTime);
    62. if (isMorningWorkingHour || isAfternoonWorkingHour) {
    63. totalHours += 0.5;
    64. }
    65. }
    66. currentDateTime = currentDateTime.plusMinutes(30);//此处设置的步进是30分钟,可以根据自己需求进行调整,但调整的时候需要同步对totalHours的定义、步进进行调整
    67. }
    68. return totalHours;
    69. }
    70. private boolean isWeekend(LocalDate date) {
    71. DayOfWeek dayOfWeek = date.getDayOfWeek();
    72. return dayOfWeek == DayOfWeek.SATURDAY || dayOfWeek == DayOfWeek.SUNDAY;
    73. }
    74. private boolean isSpecialRestDay(LocalDate date) {
    75. return specialRestDays.contains(date);
    76. }
    77. }

  • 相关阅读:
    [安洵杯 2019]不是文件上传
    将JavaBean交给IoC容器管理和依赖注入DI
    【设计模式】建造者模式
    2-FreeRTOS编码标准、风格指南
    论文解读:PromptBERT: Improving BERT Sentence Embeddings with Prompts
    BUUCTF [BJDCTF2020]鸡你太美 1
    Glide:DecodeJob
    Python+大数据-知行教育(三)-访问咨询主题看板_增量流程
    《MySQL DBA封神打怪之路》专栏学习大纲
    jsoncpp库的使用及用httplib库搭建HTTP服务器
  • 原文地址:https://blog.csdn.net/chichuhanga/article/details/133080398