admin管理员组

文章数量:1431726

I'm trying to set a date to 7 working days from today's date (excluding weekends and UK public holidays).

  1. I start by setting the default date to today's date (todaysDate) + 7 days (todayPlusSevenDays)
  2. Then I count the number of weekend days between todaysDate & todayPlusSevenDays If I find any I add them to todayPlusSevenDays
  3. Then I check for public holidays and if I find any I also add them

After performing those checks I have now added extra days to my default date - how can I also check if that new range of days contains weekend or public holidays?

For instance, if the default date bees a weekend or bank holiday it should also add more days (right now it doesn't).

Here is my code so far: /

function prepopulateDropdown() {
    var todaysDate = new Date(),
        tempNewDate = new Date(),
        todayPlusSevenDays,
        numberOfWeekends,
        todayPlusSevenDaysPlusWeekends,
        currentHour = todaysDate.getHours(),
        holidayCount = 0,
        weekendDayCount = 0,
        ukHolidays = ['2017-05-12','2017-05-29','2017-08-28','2017-12-25','2017-12-26'];

    // check if current time < or > 6pm GMT
    function setDefaultdDate(){
     if(currentHour >= 18){
           todayPlusSevenDays = new Date(tempNewDate.setDate(tempNewDate.getDate() + 7));
       }
       else{
           todayPlusSevenDays = new Date(tempNewDate.setDate(tempNewDate.getDate() + 6));
       }
    }
    setDefaultdDate();

    // Weekend day count
    function calculateWeekendDays(startDate, endDate){
        while(startDate < endDate){
            startDate.setDate(startDate.getDate() + 1);
            if(startDate.getDay() === 0 || startDate.getDay() == 6){
                ++weekendDayCount ;
            }
        }
        return weekendDayCount;
    }
    calculateWeekendDays(todaysDate, todayPlusSevenDays);

    todayPlusSevenDaysPlusWeekends = new Date(tempNewDate.setDate(tempNewDate.getDate() + weekendDayCount));



    // count UK bank holidays within todayPlusSevenDays
    function calculateBankHolidays(startDate, endDate){
      startDate.setHours(0,0,0,0);
      endDate.setHours(0,0,0,0);

      for(i=0; i < ukHolidays.length; i++){
        ukHolidaysFormated = new Date(ukHolidays[i]).setHours(0,0,0,0);
        d = new Date(ukHolidays[i]).getDay();

        if (ukHolidaysFormated >= startDate && ukHolidaysFormated <= endDate && !(d == 0 || d == 6)) {
           holidayCount++;
        }
      }
      return holidayCount;
    }
    calculateBankHolidays(todaysDate, todayPlusSevenDaysPlusWeekends);

    todayPlusSevenDaysPlusWeekends = new Date(todayPlusSevenDaysPlusWeekends.setDate(todayPlusSevenDaysPlusWeekends.getDate() + holidayCount));


    // set date to prepopulate
    var today = new Date();
    var year = todayPlusSevenDaysPlusWeekends.getFullYear();
    var month = '0' + (todayPlusSevenDaysPlusWeekends.getMonth() + 1);
    var day = todayPlusSevenDaysPlusWeekends.getDate();

    $('.slctDay option').each(function(){
        if($(this).val() == day){
            $(this).attr('selected','selected');
        }
    });
    $('.slctMonth option').each(function(){
        if($(this).val() == month){
            $(this).attr('selected','selected');
        }
    });
    $('.slctYear option').each(function(){
        if($(this).val() == year){
            $(this).attr('selected','selected');
        }
    });
}

I'm trying to set a date to 7 working days from today's date (excluding weekends and UK public holidays).

  1. I start by setting the default date to today's date (todaysDate) + 7 days (todayPlusSevenDays)
  2. Then I count the number of weekend days between todaysDate & todayPlusSevenDays If I find any I add them to todayPlusSevenDays
  3. Then I check for public holidays and if I find any I also add them

After performing those checks I have now added extra days to my default date - how can I also check if that new range of days contains weekend or public holidays?

For instance, if the default date bees a weekend or bank holiday it should also add more days (right now it doesn't).

Here is my code so far: https://jsfiddle/7yxna052/

function prepopulateDropdown() {
    var todaysDate = new Date(),
        tempNewDate = new Date(),
        todayPlusSevenDays,
        numberOfWeekends,
        todayPlusSevenDaysPlusWeekends,
        currentHour = todaysDate.getHours(),
        holidayCount = 0,
        weekendDayCount = 0,
        ukHolidays = ['2017-05-12','2017-05-29','2017-08-28','2017-12-25','2017-12-26'];

    // check if current time < or > 6pm GMT
    function setDefaultdDate(){
     if(currentHour >= 18){
           todayPlusSevenDays = new Date(tempNewDate.setDate(tempNewDate.getDate() + 7));
       }
       else{
           todayPlusSevenDays = new Date(tempNewDate.setDate(tempNewDate.getDate() + 6));
       }
    }
    setDefaultdDate();

    // Weekend day count
    function calculateWeekendDays(startDate, endDate){
        while(startDate < endDate){
            startDate.setDate(startDate.getDate() + 1);
            if(startDate.getDay() === 0 || startDate.getDay() == 6){
                ++weekendDayCount ;
            }
        }
        return weekendDayCount;
    }
    calculateWeekendDays(todaysDate, todayPlusSevenDays);

    todayPlusSevenDaysPlusWeekends = new Date(tempNewDate.setDate(tempNewDate.getDate() + weekendDayCount));



    // count UK bank holidays within todayPlusSevenDays
    function calculateBankHolidays(startDate, endDate){
      startDate.setHours(0,0,0,0);
      endDate.setHours(0,0,0,0);

      for(i=0; i < ukHolidays.length; i++){
        ukHolidaysFormated = new Date(ukHolidays[i]).setHours(0,0,0,0);
        d = new Date(ukHolidays[i]).getDay();

        if (ukHolidaysFormated >= startDate && ukHolidaysFormated <= endDate && !(d == 0 || d == 6)) {
           holidayCount++;
        }
      }
      return holidayCount;
    }
    calculateBankHolidays(todaysDate, todayPlusSevenDaysPlusWeekends);

    todayPlusSevenDaysPlusWeekends = new Date(todayPlusSevenDaysPlusWeekends.setDate(todayPlusSevenDaysPlusWeekends.getDate() + holidayCount));


    // set date to prepopulate
    var today = new Date();
    var year = todayPlusSevenDaysPlusWeekends.getFullYear();
    var month = '0' + (todayPlusSevenDaysPlusWeekends.getMonth() + 1);
    var day = todayPlusSevenDaysPlusWeekends.getDate();

    $('.slctDay option').each(function(){
        if($(this).val() == day){
            $(this).attr('selected','selected');
        }
    });
    $('.slctMonth option').each(function(){
        if($(this).val() == month){
            $(this).attr('selected','selected');
        }
    });
    $('.slctYear option').each(function(){
        if($(this).val() == year){
            $(this).attr('selected','selected');
        }
    });
}
Share Improve this question edited May 3, 2017 at 19:29 Tasos K. 8,0977 gold badges42 silver badges65 bronze badges asked May 3, 2017 at 18:25 JohnJohn 3,80914 gold badges44 silver badges49 bronze badges 1
  • Probably duplicate of Add Working Days Using Javascript. – RobG Commented May 4, 2017 at 6:34
Add a ment  | 

3 Answers 3

Reset to default 3

Here is an example of what @andi is talking about. I made it as a calculator object.

var calculator = {
    workDaysAdded: 0,
    ukHolidays: ['2017-05-12','2017-05-29','2017-08-28','2017-12-25','2017-12-26'],
    startDate: null,
    curDate: null,

    addWorkDay: function() {
        this.curDate.setDate(this.curDate.getDate() + 1);
        if(this.ukHolidays.indexOf(this.formatDate(this.curDate)) === -1 && this.curDate.getDay() !== 0 && this.curDate.getDay() !== 6) {
            this.workDaysAdded++;
        }
    },

    formatDate: function(date) {
        var day = date.getDate(),
            month = date.getMonth() + 1;

        month = month > 9 ? month : '0' + month;
        day = day > 9 ? day : '0' + day;
        return date.getFullYear() + '-' + month + '-' + day;
    },

    getNewWorkDay: function(daysToAdd) {
        this.startDate = new Date();
        this.curDate = new Date();
        this.workDaysAdded = 0;
        
        while(this.workDaysAdded < daysToAdd) {
            this.addWorkDay();
        }
        return this.curDate;
    }
}

var newWorkDay7 = calculator.getNewWorkDay(7);
var newWorkDay9 = calculator.getNewWorkDay(9);
var newWorkDay14 = calculator.getNewWorkDay(14);
console.log(newWorkDay7);
console.log(newWorkDay9);
console.log(newWorkDay14);

Check one day at a time instead of a 7 day range.

Start by setting the default date to today's date. Then, check one day at a time into the future. If that day is a working day, increment the workingDay counter by 1. if it's not, just loop onto the following day. When your workingDay counter hits 7, that's the date you need.

If you only want to add 7 days and exclude holidays and weekends (assuming Saturday and Sunday), then you can just step from the start to the end and test each day as you go:

var ukHolidays = ['2017-05-12','2017-05-29','2017-08-28','2017-12-25','2017-12-26'];

// Return date string in format YYYY-MM-DD
function getISODate(date){
  function z(n) {return (n<10?'0':'')+n}
  return date.getFullYear() + '-' + z(date.getMonth() + 1) + '-' + z(date.getDate());  
}

// Modifies date by adding 7 days, excluding sat, sun and UK holidays
function add7WorkingDays(date) {
  for (var i=7; i; i--) {
    // Add a day
    date.setDate(date.getDate() + 1);

    // If a weekend or holiday, keep adding until not
    while(!(date.getDay()%6) || ukHolidays.indexOf(getISODate(date)) != -1) {
      date.setDate(date.getDate() + 1);
    }
  }
  return date;
}

// Add 7 working days to today
var d = new Date();
console.log('Add 7 working days to ' + d.toString() + 
            '\nResult: ' + add7WorkingDays(d).toString());

本文标签: javascriptSet date to 7 working days from today (excluding weekends and public holidays)Stack Overflow