How to calculate Number of 'Working days' between two dates in Javascript using moment.js?

前端 未结 7 2032
我寻月下人不归
我寻月下人不归 2020-12-31 05:21

How to calculate the number of working days between two dates in JavaScript using moment.js. I have a working formula that calculate these days, but the formula does not sat

相关标签:
7条回答
  • 2020-12-31 05:51

    I have been used a useful library moment-business-days coupled with moment

    NPM Link of Moment-business-days

    NPM Link of Moment

    Sample of how many business days between

    const diff = moment('05-15-2017', 'MM-DD-YYYY').businessDiff(moment('05-08-2017','MM-DD-YYYY'));
    // diff = 5
    
    0 讨论(0)
  • 2020-12-31 05:52

    I've made an adaptation to Kokizzu answer, in order to fix a Summer Time problem. In Brazilian Timezone (GMT -3), the difference between 17/10/2017 and 18/10/2017 was -2.71 instead of 2.

    The start of the week was 15/10/2017 00:00 UTC or 14/10/2017 21:00-03:00

    The end of the week was 22/10/2017 00:00 UTC or 21/10/2017 22:00-02:00 (Summer Time)

    Therefore, instead of 7, the difference between "first" and "last" variable in days was 6 (or 8, depending on your Timezone).

    The code fixed is below:

    start = moment(start).utc().add(start.utcOffset(), 'm'); // Ignore timezones
    end = moment(end).utc().add(end.utcOffset(), 'm'); // Ignore timezones
    
    var first = start.clone().endOf('week'); // end of first week
    var last = end.clone().startOf('week'); // start of last week
    
    // Fixing Summer Time problems
    firstCorrection = moment(first).utc().add(60, 'm').toDate(); //
    var days = last.diff(firstCorrection,'days') * 5 / 7; // this will always multiply of 7
    
    var wfirst = first.day() - start.day(); // check first week
    if(start.day() == 0) --wfirst; // -1 if start with sunday
    var wlast = end.day() - last.day(); // check last week
    if(end.day() == 6) --wlast; // -1 if end with saturday
    return wfirst + days + wlast; // get the total (subtract holidays if needed)
    
    0 讨论(0)
  • 2020-12-31 05:55

    I use a simple function to accomplish that. Maybe is not the most efficient but it works. It doesn't require Moment.js. it's just Javascript.

    function getNumWorkDays(startDate, endDate) {
        var numWorkDays = 0;
        var currentDate = new Date(startDate);
        while (currentDate <= endDate) {
            // Skips Sunday and Saturday
            if (currentDate.getDay() !== 0 && currentDate.getDay() !== 6) {
                numWorkDays++;
            }
            currentDate = currentDate.addDays(1);
        }
        return numWorkDays;
    }
    

    To addDays, I use the following function:

    Date.prototype.addDays = function (days) {
        var date = new Date(this.valueOf());
        date.setDate(date.getDate() + days);
        return date;
    };
    
    0 讨论(0)
  • 2020-12-31 05:58

    By using momentjs, it's possible this way:

    private calculateWorkdays(startDate: Date, endDate: Date): number {
    // + 1 cause diff returns the difference between two moments, in this case the day itself should be included.
    
    const totalDays: number = moment(endDate).diff(moment(startDate), 'days') + 1;
    const dayOfWeek = moment(startDate).isoWeekday();
    let totalWorkdays = 0;
    
    for (let i = dayOfWeek; i < totalDays + dayOfWeek; i++) {
        if (i % 7 !== 6 && i % 7 !== 0) {
          totalWorkdays++;
        }
      }
      return totalWorkdays;
    }
    
    0 讨论(0)
  • 2020-12-31 05:59

    I found kokizzu's answer didn't work if days were in the same week (e.g. sun to sat), so settled for this instead :

        function calcBusinessDays(startDate, endDate) { 
          var day = moment(startDate);
          var businessDays = 0;
    
          while (day.isSameOrBefore(endDate,'day')) {
            if (day.day()!=0 && day.day()!=6) businessDays++;
            day.add(1,'d');
          }
          return businessDays;
        }
    
    0 讨论(0)
  • 2020-12-31 06:04

    Just divide it into 3 parts.. first week, last week and the in between, something like this:

    function workday_count(start,end) {
      var first = start.clone().endOf('week'); // end of first week
      var last = end.clone().startOf('week'); // start of last week
      var days = last.diff(first,'days') * 5 / 7; // this will always multiply of 7
      var wfirst = first.day() - start.day(); // check first week
      if(start.day() == 0) --wfirst; // -1 if start with sunday 
      var wlast = end.day() - last.day(); // check last week
      if(end.day() == 6) --wlast; // -1 if end with saturday
      return wfirst + Math.floor(days) + wlast; // get the total
    } //              ^ EDIT: if days count less than 7 so no decimal point
    

    The test code

    var ftest = {date:'2015-02-0',start:1,end:7};
    var ltest = {date:'2015-02-2',start:2,end:8};
    var f = 'YYYY-MM-DD';
    for(var z=ftest.start; z<=ftest.end; ++z) {
      var start = moment(ftest.date + z);
      for(var y=ltest.start; y<=ltest.end; ++y) {
        var end = moment(ltest.date + y);
        var wd = workday_count(start,end);
        console.log('from: '+start.format(f),'to: '+end.format(f),'is '+wd+' workday(s)');
      }
    }
    

    Output of test code:

    from: 2015-02-01 to: 2015-02-22 is 15 workday(s)
    from: 2015-02-01 to: 2015-02-23 is 16 workday(s)
    from: 2015-02-01 to: 2015-02-24 is 17 workday(s)
    from: 2015-02-01 to: 2015-02-25 is 18 workday(s)
    from: 2015-02-01 to: 2015-02-26 is 19 workday(s)
    from: 2015-02-01 to: 2015-02-27 is 20 workday(s)
    from: 2015-02-01 to: 2015-02-28 is 20 workday(s)
    from: 2015-02-02 to: 2015-02-22 is 15 workday(s)
    from: 2015-02-02 to: 2015-02-23 is 16 workday(s)
    from: 2015-02-02 to: 2015-02-24 is 17 workday(s)
    from: 2015-02-02 to: 2015-02-25 is 18 workday(s)
    from: 2015-02-02 to: 2015-02-26 is 19 workday(s)
    from: 2015-02-02 to: 2015-02-27 is 20 workday(s)
    from: 2015-02-02 to: 2015-02-28 is 20 workday(s)
    from: 2015-02-03 to: 2015-02-22 is 14 workday(s)
    from: 2015-02-03 to: 2015-02-23 is 15 workday(s)
    from: 2015-02-03 to: 2015-02-24 is 16 workday(s)
    from: 2015-02-03 to: 2015-02-25 is 17 workday(s)
    from: 2015-02-03 to: 2015-02-26 is 18 workday(s)
    from: 2015-02-03 to: 2015-02-27 is 19 workday(s)
    from: 2015-02-03 to: 2015-02-28 is 19 workday(s)
    from: 2015-02-04 to: 2015-02-22 is 13 workday(s)
    from: 2015-02-04 to: 2015-02-23 is 14 workday(s)
    from: 2015-02-04 to: 2015-02-24 is 15 workday(s)
    from: 2015-02-04 to: 2015-02-25 is 16 workday(s)
    from: 2015-02-04 to: 2015-02-26 is 17 workday(s)
    from: 2015-02-04 to: 2015-02-27 is 18 workday(s)
    from: 2015-02-04 to: 2015-02-28 is 18 workday(s)
    from: 2015-02-05 to: 2015-02-22 is 12 workday(s)
    from: 2015-02-05 to: 2015-02-23 is 13 workday(s)
    from: 2015-02-05 to: 2015-02-24 is 14 workday(s)
    from: 2015-02-05 to: 2015-02-25 is 15 workday(s)
    from: 2015-02-05 to: 2015-02-26 is 16 workday(s)
    from: 2015-02-05 to: 2015-02-27 is 17 workday(s)
    from: 2015-02-05 to: 2015-02-28 is 17 workday(s)
    from: 2015-02-06 to: 2015-02-22 is 11 workday(s)
    from: 2015-02-06 to: 2015-02-23 is 12 workday(s)
    from: 2015-02-06 to: 2015-02-24 is 13 workday(s)
    from: 2015-02-06 to: 2015-02-25 is 14 workday(s)
    from: 2015-02-06 to: 2015-02-26 is 15 workday(s)
    from: 2015-02-06 to: 2015-02-27 is 16 workday(s)
    from: 2015-02-06 to: 2015-02-28 is 16 workday(s)
    from: 2015-02-07 to: 2015-02-22 is 10 workday(s)
    from: 2015-02-07 to: 2015-02-23 is 11 workday(s)
    from: 2015-02-07 to: 2015-02-24 is 12 workday(s)
    from: 2015-02-07 to: 2015-02-25 is 13 workday(s)
    from: 2015-02-07 to: 2015-02-26 is 14 workday(s)
    from: 2015-02-07 to: 2015-02-27 is 15 workday(s)
    from: 2015-02-07 to: 2015-02-28 is 15 workday(s)
    
    0 讨论(0)
提交回复
热议问题