如何将工作日添加到 Java 中的当前日期?

新手上路,请多包涵

如何将工作日添加到 Java 中的当前日期?

 public Calendar addBusinessDate(Calendar cal, int days) {
//
// code goes over here
//
}

笔记:

它也应该考虑周末。

原文由 Anand 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 413
2 个回答

您可能需要考虑使用 ObjectLab 套件 来为您完成繁重的工作。

假设要求只是在计算日期为非工作日时返回下一个工作日:

 package bizdays.example;

import java.time.LocalDate;
import java.util.HashSet;
import net.objectlab.kit.datecalc.common.DateCalculator;
import net.objectlab.kit.datecalc.common.DefaultHolidayCalendar;
import net.objectlab.kit.datecalc.common.HolidayHandlerType;
import net.objectlab.kit.datecalc.jdk8.LocalDateKitCalculatorsFactory;
import static org.junit.Assert.assertThat;
import org.junit.Before;
import org.junit.Test;
import static org.hamcrest.Matchers.equalTo;

public class BizDayTest {
    private DateCalculator<LocalDate> dateCalculator;
    private final LocalDate startDate = LocalDate.of(2009, 12, 23);

    @Before
    public void setUp() {
        HashSet<LocalDate> holidays = new HashSet<LocalDate>();
        holidays.add(LocalDate.of(2009, 12, 25));  // Friday

        DefaultHolidayCalendar<LocalDate> holidayCalendar =
            new DefaultHolidayCalendar<LocalDate>(holidays);

        LocalDateKitCalculatorsFactory.getDefaultInstance()
                .registerHolidays("example", holidayCalendar);
        dateCalculator = LocalDateKitCalculatorsFactory.getDefaultInstance()
                .getDateCalculator("example", HolidayHandlerType.FORWARD);
        dateCalculator.setStartDate(startDate);
    }

    @Test
    public void should_not_change_calendar_start_date_even_after_moving() {
        assertThat(
            dateCalculator.moveByBusinessDays(6).getStartDate(),
            equalTo(startDate));
    }

    @Test
    public void moveByBusinessDays_will_return_24_dec_2009_as_next_business_day() {
        assertThat(
            dateCalculator.moveByBusinessDays(1).getCurrentBusinessDate(),
            equalTo(LocalDate.of(2009, 12, 24)));
    }

    @Test
    public void moveByBusinessDays_will_return_28_dec_2009_as_two_business_days_later() {
        assertThat(
            dateCalculator.moveByBusinessDays(2).getCurrentBusinessDate(),
            equalTo(LocalDate.of(2009, 12, 28)));

    }

    @Test
    public void moveByDays_will_also_return_28_dec_2009_as_two_business_days_later() {
        assertThat(
            dateCalculator.moveByDays(2).getCurrentBusinessDate(),
            equalTo(LocalDate.of(2009, 12, 28)));
    }

    @Test
    public void moveByBusinessDays_will_exclude_25_26_and_27_dec_when_computing_business_days() {
        assertThat(
            dateCalculator.moveByBusinessDays(5).getCurrentBusinessDate(),
            equalTo(LocalDate.of(2009, 12, 31)));
    }

    @Test
    public void moveByDays_will_include_25_26_and_27_dec_when_computing_business_days() {
        assertThat(
            dateCalculator.moveByDays(5).getCurrentBusinessDate(),
            equalTo(LocalDate.of(2009, 12, 28)));
    }
}

图书馆默认工作周为周一至周五,但您可以通过提供自定义 WorkingWeekDateCalculatorsetWorkingWeek() .

如最后两个示例所示, moveByDays() 在移动日期时包括周末,而 moveByBusinessDays() 不包括周末。

该库还允许您使用 java.util.CalendarJoda TimeLocalDate 。这些示例使用 JDK8 的 java.time.LocalDate 因为它是自 JDK8 以来的首选方式。

编辑:更新示例以使用 java.time.LocalDate

原文由 shaolang 发布,翻译遵循 CC BY-SA 4.0 许可协议

利用:

 public Calendar addBusinessDate(Calendar cal, int numBusinessDays) {
  int numNonBusinessDays = 0;

  for(int i = 0; i < numBusinessDays; i++) {
    cal.add(Calendar.DATE, 1);

    /*
       It's a Canadian/American custom to get the Monday (sometimes Friday) off
       when a holiday falls on a weekend.
    */
    for(int j = 0; j < holidays; j++) { //holidays is list of dates
      if(cal.getTime() == (Date)holidays.get(j)) {
        numNonBusinessDays++;
      }
    }

    if(cal.get(Calendar.DAY_OF_WEEK) == 1 ||
       cal.get(Calendar.DAY_OF_WEEK) == 7) {
      numNonBusinessDays++;
    }
  }

  if(numNonBusinessDays > 0) {
    cal.add(Calendar.DATE, numNonBusinessDays);
  }

  return cal;
}

您必须填充日期列表才能处理假期。有像新年这样的常见节日,但例如加拿大和美国的感恩节就不同。还要注意假期可以在周末,所以周末变成了 3 天的周末。

参考:

PS:如果您像示例中那样更新值,则实际上不需要返回 Calendar 实例。但如果你想创建一个单独的 Calendar 实例,它是有效的,使用:

 public Calendar addBusinessDate(Calendar cal, int numBusinessDays) {
  Calendar cal2 = Calendar.getInstance();
  cal2.setTime(cal.getTime());

  int numNonBusinessDays = 0;

  for(int i = 0; i < numBusinessDays; i++) {
    cal2.add(Calendar.DATE, 1);

    /*
       It's a Canadian/American custom to get the Monday (sometimes Friday) off
       when a holiday falls on a weekend.
    */
    for(int j = 0; j < holidays; j++) { //holidays is list of dates
      if(cal2.getTime() == (Date)holidays.get(j)) {
        numNonBusinessDays++;
      }
    }

    if(cal2.get(Calendar.DAY_OF_WEEK) == 1 ||
       cal2.get(Calendar.DAY_OF_WEEK) == 7) {
      numNonBusinessDays++;
    }
  }

  if(numNonBusinessDays > 0) {
    cal2.add(Calendar.DATE, numNonBusinessDays);
  }

  return cal2;
}

原文由 OMG Ponies 发布,翻译遵循 CC BY-SA 2.5 许可协议

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题