手稿 - 帮一同事写的计算时间差(忽略某一天中的某些事件端)工具方法

原需求:计算两个给定的两个时间差,但是要求忽略 21:00~次日09:00。


思路:

  • 一天24小时,切换为一天12个小时。
  • 给定的两个时间预处理到,切换到一天中的 09:00 ~ 21:00(有效计算)中
  • 然后计算两个时间查:预处理之后的倆时间的差(24h) - 间隔天数*每天有效的时间(12h)
  • Test code

package com.test;

import com.sun.tools.javac.util.Assert;

import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;

/**
 * TestMain
 *
 * @author: Mr.Rookie
 */
public class TestMain {

    public static long startIndex = 9 * 60 * 60;// 9:00 unit: s
    public static long during = 12 * 60 * 60;   // start + during = 21:00 unit: s

    public final static int DAY_SECOND = 24 * 3600;

    public TestMain() {
    }

    public static void main(String args[]) throws Exception {

        testDuring();

    }

    public static void testDuring() throws Exception {
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");

        Date start  = sdf.parse("2019-01-01 22:00:00");
        Date end    = sdf.parse("2019-01-01 23:00:00");

        System.out.println(formatPrint(during(start, end)));

        end    = sdf.parse("2019-01-02 12:00:00");
        System.out.println(formatPrint(during(start, end)));


        end    = sdf.parse("2019-01-03 21:00:00");
        System.out.println(formatPrint(during(start, end)));
    }

    /**
     *
     * @param startDate
     * @param endDate
     * @return
     */
    public static long during(Date startDate, Date endDate) {

        Assert.check(endDate.compareTo(startDate) >= 0, "The endDate must be greater than startDate !!!");

        long inputStart = startDate.getTime() / 1000;
        long inputEnd   = endDate.getTime() / 1000;

        if ( inputEnd == inputStart ) {
            return 0;
        }

        long startDateTime  = getDateOffset(startDate);
        long endDateTime    = getDateOffset(endDate);
        // date during
        int dayDuring       = (int)(endDateTime -  startDateTime) / DAY_SECOND;

        // Preprocess parameters of input
        long temp = 0;
        if ( inputStart < (temp = startDateTime + startIndex) ) {
            inputStart = temp;
        } else if ( inputStart > (temp += during) ) {
            inputStart = temp;
        }

        if ( inputEnd < (temp = endDateTime + startIndex) ) {
            inputEnd = temp;
        } else if ( inputEnd > (temp += during) ) {
            inputEnd = temp;
        }

        // return result
        return (inputEnd - inputStart) - dayDuring * (DAY_SECOND - during);
    }

    /**
     * 清除指定日期的时间戳信息,并返回当前时间的偏移量,单位秒
     * @param date
     * @return
     */
    private static long getDateOffset(Date date) {
        Calendar instance = Calendar.getInstance();
        instance.setTime(date);

        // clear  timestamp
        instance.set(Calendar.HOUR_OF_DAY, 0);
        instance.set(Calendar.MINUTE, 0);
        instance.set(Calendar.SECOND, 0);
        instance.set(Calendar.MILLISECOND, 0);

        return instance.getTime().getTime() / 1000;
    }

    /**
     *
     * @param second
     * @return
     */
    private static String formatPrint(long second) {
        int day = (int)(second / DAY_SECOND); // day
        int hour = (int)(second %= DAY_SECOND) / 3600;// h
        int min = (int)(second %= 3600) / 60;
        return String.format("%02d天%02d小时%02d分%02d秒", day, hour, min, second);
    }

}

你可能感兴趣的:(手稿 - 帮一同事写的计算时间差(忽略某一天中的某些事件端)工具方法)