java组件:开始时间的N个周期结束时间的实现
根据按月、按季、按年等,计算开始时间对应的结束时间。
比如1月1号开始,周期是按月,那结束时间是什么时候?
比如1月31号开始,周期是按月,那结束时间是什么时候?
如果结束时间所在的月是2月、闰年2月、月数天数有31天,时间又如何变化?
实现:
已知开始时间和周期,需要得到一个结束时间:
private String getPeriodEndDate(String startDateStr, int period) {
Calendar endDateCalendar = getDate(startDateStr);
int startDay = endDateCalendar.get(Calendar.DAY_OF_MONTH);
// calendar会自动处理:
// 1、如果增加某些月的数量,天超过月份中最大的天数时会被减到当月的最大值;
// 2、如果减少某些天的数量,当减的天数大于月中已有的天数,则月数会减1;
// 故当增加月份后若结束日期中的天与开始日期的天不一致时,说明结束月天数不够,不需要再减;否则需要减一天;
// 一般周期都是从某天到下一个周期的该天减1,比如2018-12-24到2019-1-23就是一个周期,其中23是由24-1得来的;
// 但如果是2018-1-31到2018-2-30,由于日历组件由1月加到2月的时候,会自动减到28(闰年则减到29),此时由于天数不够故不用减,直接用28/29即可;
// 所以规律就是:日历组件加上N月之后,如果得到的天还与原来的天一样,则减1天,否则不减。
endDateCalendar.add(Calendar.MONTH, period);
int endDay = endDateCalendar.get(Calendar.DAY_OF_MONTH);
if(startDay == endDay) {
endDateCalendar.add(Calendar.DAY_OF_MONTH, -1);
}
return new SimpleDateFormat("yyyy-MM-dd").format(endDateCalendar.getTime());
}
private Calendar getDate(String dateStr) {
Date startDate = null;
try {
startDate = new SimpleDateFormat("yyyy-MM-dd").parse(dateStr);
} catch (ParseException e) {
throw new IllegalArgumentException("Invalid start date, startDateStr=" + dateStr);
}
Calendar calendar = Calendar.getInstance();
calendar.setTime(startDate);
return calendar;
}
测试:
private void testPeriodEndDate() {
System.out.println(getPeriodEndDate("2018-01-01", 1)); // 输出: 2018-01-31
System.out.println(getPeriodEndDate("2018-01-13", 1)); // 输出: 2018-02-12
System.out.println(getPeriodEndDate("2018-01-31", 1)); // 输出: 2018-02-28
System.out.println(getPeriodEndDate("2018-01-28", 1)); // 输出: 2018-02-27
System.out.println(getPeriodEndDate("2000-01-29", 1)); // 输出: 2000-02-28
}
结束时间的计算:把开始时间加上对应周期之后减一天即为结束时间,若结束时间在对应的月份不存在则减到存在的那一天。