系统考勤请假中的方法:
1、在选中时间区间后,排除掉法定的节假日、正常双休和午休的两个小时,同时将调休日算作正常工作时间。
2、最后返回的天数是double类型的,是半天或是整天。
代码部分:
1、从页面拿到开始时间和结束时间(页面用的是vue.js),当前是String类型
/** * 计算请假天数 */ @Login @RequestMapping("/calculationTime") public R calculationTime(@RequestParam Map<String, Object> params){ DateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm"); double dayTime = 0; dayTime = wxUserHolidayService.calculationTime(String.valueOf(params.get("stime")), String.valueOf(params.get("etime"))); double days = wxUserHolidayService.halfDayMath(dayTime); return R.ok().put("days",days); }
2、需要的具体方法,根据需要进行取舍
package com.hnzie.modules.kaoqin.service; import com.baomidou.mybatisplus.service.IService; import com.hnzie.modules.kaoqin.entity.WxUserHolidayEntity; import java.util.*; public interface WxUserHolidayService extends IService<WxUserHolidayEntity> {
// 获取假期日期 String[] holiday1(); // 获取调休工作日期 String[] holiday2(); // 获取除午休的工作时间 String[] workTimes(); /** * 计算请假天数,去除周末、节假日 * @param stime * @param etime */ double calculationTime(String stime, String etime); /** * 去重 * @param str */ List<String> removal(List<String> str); /** * 获取两个日期之间的所有日期,去掉周末 * @param startDate * @param endDate * @return */ List<String> getDates(String startDate, String endDate); /** * 字符串转时间 * @param dateStr * @param index * @return */ Date StringToDate(String dateStr, int index); /** * 时间转字符串 * @param date * @param index * @return */ String dateToString(Date date, int index); /** * 获取法定节假日或者调休 * @param num * @return */ List<String> holiday(int num); /** * 获取不同部门工作时间 * @return */ String[] workTime(); // 计算整天或半天 double halfDayMath(double time);
}
3、实现方法
package com.hnzie.modules.kaoqin.service.impl; import com.baomidou.mybatisplus.service.impl.ServiceImpl; import com.hnzie.modules.kaoqin.dao.WxUserHolidayDao; import com.hnzie.modules.kaoqin.entity.WxUserHolidayEntity; import com.hnzie.modules.kaoqin.service.WxQingjiaMaintainService; import com.hnzie.modules.kaoqin.service.WxUserHolidayService; import lombok.extern.slf4j.Slf4j; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import java.text.DateFormat; import java.text.SimpleDateFormat; import java.util.*; @Service("wxUserHolidayService") @Slf4j public class WxUserHolidayServiceImpl extends ServiceImpl<WxUserHolidayDao, WxUserHolidayEntity> implements WxUserHolidayService {
/** * 定义常见的时间格式 */ private static String[] dateFormat = { "yyyy-MM-dd HH:mm:ss", // 0 "yyyy/MM/dd HH:mm:ss", // 1 "yyyy年MM月dd日HH时mm分ss秒", // 2 "yyyy-MM-dd", // 3 "yyyy/MM/dd", // 4 "yy-MM-dd", // 5 "yy/MM/dd", // 6 "yyyy年MM月dd日", // 7 "HH:mm:ss", // 8 "yyyyMMddHHmmss", // 9 "yyyyMMdd", // 10 "yyyy.MM.dd", // 11 "yy.MM.dd", // 12 "MM月dd日HH时mm分", // 13 "yyyy年MM月dd日 HH:mm:ss", // 14 "yyyy-MM-dd HH:mm", // 15 "yyMMdd" // 16 }; @Override public String[] holiday1() { return baseMapper.selectLawHolidayDate(); } @Override public String[] holiday2() { return baseMapper.selectLawWorkDate(); } @Override public String[] workTimes() {
String S = baseMapper.selectTimeTable(Const.timeTableKey);
Map<String,Object> parse = (Map<String,Object>)JSON.parse(S);
String[] times = new String[4];
times[0] = String.valueOf(parse.get("SstartTime"));
times[1] = String.valueOf(parse.get("SendTime"));
times[2] = String.valueOf(parse.get("XstartTime"));
times[3] = String.valueOf(parse.get("XendTime"));
return times; } @Override public double calculationTime(String startTime, String endTime) { // 获取startTime和endTime之间的所有日期,去掉周六周日 List<String> list = this.getDates(startTime, endTime); // 获取法定节假日 List<String> fdList = this.holiday(1); // 获取调休 List<String> txList = this.holiday(2); // 上班时间 String[] workTime = this.workTime(); String[] split = workTime[2].split(":"); String[] split1 = workTime[1].split(":"); //午休时间 int wxTime = (Integer.valueOf(split[0]) - Integer.valueOf(split1[0])) * 60; // 删除时间区间中的所有法定节假日 list.removeAll(fdList); DateFormat df = new SimpleDateFormat(dateFormat[3]); String st =startTime.substring(0, 10); String en =endTime.substring(0, 10); try { Date sts =df.parse(startTime.substring(0, 10)); Date ens =df.parse(endTime.substring(0, 10)); for (String s : txList) { Date ss =df.parse(s); if ((ss.before(ens) && ss.after(sts)) || ss.equals(sts) || ss.equals(ens)) { // 添加时间区间中的所有调休日期 list.add(s); } } }catch (Exception e){ e.printStackTrace(); } // 去重 list = this.removal(list); // 开始当天上午上班时间、上午下班时间、下午上班时间、下午下班时间 String amWorkYes = startTime.substring(0, 11) + workTime[0]; String amWorkNo = startTime.substring(0, 11) + workTime[1]; String pmWorkYes = startTime.substring(0, 11) + workTime[2]; String pmWorkNo = startTime.substring(0, 11) + workTime[3]; // 结束当天上午上班时间、上午下班时间、下午上班时间、下午下班时间 String amWorkYesEnd = endTime.substring(0, 11) + workTime[0]; String amWorkNoEnd = endTime.substring(0, 11) + workTime[1]; String pmWorkYesEnd = endTime.substring(0, 11) + workTime[2]; String pmWorkNoEnd = endTime.substring(0, 11) + workTime[3]; double time = 0; if (list.size() == 0) { // 申请日期是法定节假日 return time; } else if (list.size() == 1) { // 请假一天 if (startTime.compareTo(pmWorkNo) > 0) { return time; } if (endTime.compareTo(amWorkYes) < 0) { return time; } if (startTime.compareTo(amWorkNo) >= 0 && endTime.compareTo(pmWorkYes) <= 0) { return time; } // 开始时间小于上午上班时间,开始时间等于上午上班时间 if (startTime.compareTo(amWorkYes) < 0) { startTime = amWorkYes; } // 结束时间大于下午下班时间,结束时间等于下午下班时间 if (endTime.compareTo(pmWorkNo) > 0) { endTime = pmWorkNo; } // 开始时间大于上午下班时间,小于下午上班时间,开始时间等于下午上班时间 if (startTime.compareTo(amWorkNo) >= 0 && startTime.compareTo(pmWorkYes) <= 0) { startTime = pmWorkYes; } // 结束时间大于上午下班时间,小于下午上班时间,结束时间等于上午下班时间 if (endTime.compareTo(amWorkNo) >= 0 && endTime.compareTo(pmWorkYes) <= 0) { endTime = amWorkNo; } Date start = this.StringToDate(startTime, 15); // 0或者15 Date end = this.StringToDate(endTime, 15); // 三种情况,1:请假时间全在上午,2:请假时间全在下午,3:包含午休时间 if (startTime.compareTo(amWorkYes) >= 0 && endTime.compareTo(amWorkNo) <= 0) { double minute = (end.getTime() - start.getTime()) / (1000 * 60); time = minute / (8 * 60); } else if (startTime.compareTo(pmWorkYes) >= 0 && endTime.compareTo(pmWorkNo) <= 0) { double minute = (end.getTime() - start.getTime()) / (1000 * 60); time = minute / (8 * 60); } else if (startTime.compareTo(amWorkNo) < 0 && endTime.compareTo(pmWorkYes) > 0) { double minute = (end.getTime() - start.getTime()) / (1000 * 60) - wxTime; time = minute / (8 * 60); } return time; } else { // 处理请假多天的情况 // 申请开始时间处理 if (list.contains(st)) { if (startTime.compareTo(amWorkYes) < 0) { startTime = amWorkYes; } if (startTime.compareTo(pmWorkNo) > 0) { startTime = pmWorkNo; } if (startTime.compareTo(amWorkNo) >= 0 && startTime.compareTo(pmWorkYes) <= 0) { startTime = pmWorkYes; } Date start = this.StringToDate(startTime, 15); // 0或者15 Date end = this.StringToDate(pmWorkNo, 15); if (startTime.compareTo(amWorkNo) < 0) { // 减去中午一小时 double t = (end.getTime() - start.getTime()) / (1000 * 60) - wxTime; time = time + t / (8 * 60); } else { double t = (end.getTime() - start.getTime()) / (1000 * 60); time = time + t / (8 * 60); } list.remove(st); } // 申请结束时间处理 if (list.contains(en)) { if (endTime.compareTo(amWorkYesEnd) < 0) { endTime = amWorkYesEnd; } if (endTime.compareTo(pmWorkNoEnd) > 0) { endTime = pmWorkNoEnd; } if (endTime.compareTo(amWorkNoEnd) >= 0 && endTime.compareTo(pmWorkYesEnd) <= 0) { endTime = amWorkNoEnd; } Date end = this.StringToDate(endTime, 15);// 0或者15 Date start = this.StringToDate(amWorkYesEnd, 15); if (endTime.compareTo(pmWorkYesEnd) > 0) { double t = (end.getTime() - start.getTime()) / (1000 * 60) - wxTime; time = time + t / (8 * 60); } else { double t = (end.getTime() - start.getTime()) / (1000 * 60); time = time + t / (8 * 60); } list.remove(en); } // 天数计算集合中剩下的个数就可以 time = time + list.size(); return time; } } /** * 去重 * @param str */ @Override public List<String> removal(List<String> str) { Set<String> s = new HashSet<String>(str); str.clear(); str.addAll(s); return str; } /** * 获取两个日期之间的所有日期,去掉周末 * @param startDate * @param endDate */ @Override public List<String> getDates(String startDate, String endDate) { List<String> result = new ArrayList<String>(); Calendar startDay = Calendar.getInstance(); Calendar endDay = Calendar.getInstance(); startDay.setTime(StringToDate(startDate, 3)); endDay.setTime(StringToDate(endDate, 3)); while (startDay.before(endDay)) { int week = startDay.get(Calendar.DAY_OF_WEEK); if (7 != week && 1 != week) { result.add(dateToString(startDay.getTime(), 3)); } startDay.add(Calendar.DAY_OF_YEAR, 1); } // 验证结束日期是否是周六周日 int week = endDay.get(Calendar.DAY_OF_WEEK); if (7 != week && 1 != week) { result.add(dateToString(endDay.getTime(), 3)); } return result; } /** * 字符串转时间 * @param dateStr * @param index */ @Override public Date StringToDate(String dateStr, int index) { DateFormat df = null; try { df = new SimpleDateFormat(dateFormat[index]); return df.parse(dateStr); } catch (Exception aioe) { return null; } } /** * 时间转字符串 * @param date * @param index */ @Override public String dateToString(Date date, int index) { if (date == null) { return null; } return new SimpleDateFormat(dateFormat[index]).format(date); } /** * 获取法定节假日或者调休 * @param num */ @Override public List<String> holiday(int num) { if (num == 2) { return Arrays.asList(this.holiday2()); } else { return Arrays.asList(this.holiday1()); } } /** * 获取不同部门工作时间 */ @Override public String[] workTime() { return this.workTimes(); } @Override public double halfDayMath(double time){ String timeStr = time+""; System.out.println("timeStr = [" + timeStr + "]"); String[] timeArr = timeStr.split("\\."); int t1 = Integer.valueOf(timeArr[0]); System.out.println("t1 = [" + t1 + "]"); int t2 = Integer.valueOf(timeArr[1].substring(0, 1)); System.out.println("t2 = [" + t2 + "]"); if (t2 < 5){ return t1; }else if (t2>5){ t1++; return t1; }else { return t1+0.5f; } } }
4、dao层的方法
package com.hnzie.modules.kaoqin.dao; import com.baomidou.mybatisplus.mapper.BaseMapper; import com.hnzie.modules.kaoqin.entity.WxUserHolidayEntity; import org.apache.ibatis.annotations.Param; public interface WxUserHolidayDao extends BaseMapper<WxUserHolidayEntity> { //查询所有节假日 String[] selectLawHolidayDate(); //查询所有调休(上班)日 String[] selectLawWorkDate(); String selectTimeTable(@Param("key") String key); }
5、mapper中sql语句
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="com.hnzie.modules.kaoqin.dao.WxUserHolidayDao"> <select id="selectLawHolidayDate" resultType="String"> select time from wx_kq_qingjia_maintain where del_flag = 0 and time_type = 2 </select> <select id="selectLawWorkDate" resultType="String"> select time from wx_kq_qingjia_maintain where del_flag = 0 and time_type = 1 </select>
<!-- 配置表中查询的工作时间 --> <select id="selectTimeTable" resultType="String"> select param_value as paramValue from sys_config where status = 1 and param_key = #{key} </select> </mapper>
节假日和调休日需要读取放在数据库中的数据
只排除节假日和周六日的https://blog.csdn.net/wujian_csdn_csdn/article/details/86480234