查找两个日期之间的差异(周末除外)

时间:2010-08-12 02:06:38

标签: javascript jquery-ui

您好我正在使用jquery-ui datepicker来选择日期和date.js来查找2个日期之间的差异。

现在问题是我想从计算中排除周末天数(星期六和星期日)。我该怎么做?

例如,用户选择开始日期(13/8/2010)和结束日期(16/8/2010)。由于2010年8月14日和2010年8月15日是工作日,而不是总共4天,我希望它只有2天。

这是我现在使用的代码:

<script type="text/javascript">

    $("#startdate, #enddate").change(function() {       

    var d1 = $("#startdate").val();
    var d2 = $("#enddate").val();

            var minutes = 1000*60;
            var hours = minutes*60;
            var day = hours*24;

            var startdate1 = getDateFromFormat(d1, "d-m-y");
            var enddate1 = getDateFromFormat(d2, "d-m-y");

            var days = 1 + Math.round((enddate1 - startdate1)/day);             

    if(days>0)
    { $("#noofdays").val(days);}
    else
    { $("#noofdays").val(0);}


    });

    </script>

11 个答案:

答案 0 :(得分:18)

也许其他人可以帮助您将此功能转换为JQuery的框架......

我找到了这个函数here

function calcBusinessDays(dDate1, dDate2) { // input given as Date objects
  var iWeeks, iDateDiff, iAdjust = 0;
  if (dDate2 < dDate1) return -1; // error code if dates transposed
  var iWeekday1 = dDate1.getDay(); // day of week
  var iWeekday2 = dDate2.getDay();
  iWeekday1 = (iWeekday1 == 0) ? 7 : iWeekday1; // change Sunday from 0 to 7
  iWeekday2 = (iWeekday2 == 0) ? 7 : iWeekday2;
  if ((iWeekday1 > 5) && (iWeekday2 > 5)) iAdjust = 1; // adjustment if both days on weekend
  iWeekday1 = (iWeekday1 > 5) ? 5 : iWeekday1; // only count weekdays
  iWeekday2 = (iWeekday2 > 5) ? 5 : iWeekday2;

  // calculate differnece in weeks (1000mS * 60sec * 60min * 24hrs * 7 days = 604800000)
  iWeeks = Math.floor((dDate2.getTime() - dDate1.getTime()) / 604800000)

  if (iWeekday1 < iWeekday2) { //Equal to makes it reduce 5 days
    iDateDiff = (iWeeks * 5) + (iWeekday2 - iWeekday1)
  } else {
    iDateDiff = ((iWeeks + 1) * 5) - (iWeekday1 - iWeekday2)
  }

  iDateDiff -= iAdjust // take into account both days on weekend

  return (iDateDiff + 1); // add 1 because dates are inclusive
}

var date1 = new Date("August 11, 2010 11:13:00");
var date2 = new Date("August 16, 2010 11:13:00");
alert(calcBusinessDays(date1, date2));

## EDITED ##

如果您想将它与您的格式一起使用:

您的代码如下:

function calcBusinessDays(dDate1, dDate2) { // input given as Date objects
  var iWeeks, iDateDiff, iAdjust = 0;
  if (dDate2 < dDate1) return -1; // error code if dates transposed
  var iWeekday1 = dDate1.getDay(); // day of week
  var iWeekday2 = dDate2.getDay();
  iWeekday1 = (iWeekday1 == 0) ? 7 : iWeekday1; // change Sunday from 0 to 7
  iWeekday2 = (iWeekday2 == 0) ? 7 : iWeekday2;
  if ((iWeekday1 > 5) && (iWeekday2 > 5)) iAdjust = 1; // adjustment if both days on weekend
  iWeekday1 = (iWeekday1 > 5) ? 5 : iWeekday1; // only count weekdays
  iWeekday2 = (iWeekday2 > 5) ? 5 : iWeekday2;

  // calculate differnece in weeks (1000mS * 60sec * 60min * 24hrs * 7 days = 604800000)
  iWeeks = Math.floor((dDate2.getTime() - dDate1.getTime()) / 604800000)

  if (iWeekday1 < iWeekday2) { //Equal to makes it reduce 5 days
    iDateDiff = (iWeeks * 5) + (iWeekday2 - iWeekday1)
  } else {
    iDateDiff = ((iWeeks + 1) * 5) - (iWeekday1 - iWeekday2)
  }

  iDateDiff -= iAdjust // take into account both days on weekend

  return (iDateDiff + 1); // add 1 because dates are inclusive
}


$("#startdate, #enddate").change(function() {

  var d1 = $("#startdate").val();
  var d2 = $("#enddate").val();

  var minutes = 1000 * 60;
  var hours = minutes * 60;
  var day = hours * 24;

  var startdate1 = new Date(d1);
  var enddate1 = new Date(d2);


  var newstartdate = new Date();
  newstartdate.setFullYear(startdate1.getYear(), startdate1.getMonth(), startdate1.getDay());
  var newenddate = new Date();
  newenddate.setFullYear(enddate1.getYear(), enddate1.getMonth(), enddate1.getDay());
  var days = calcBusinessDays(newstartdate, newenddate);
  if (days > 0) {
    $("#noofdays").val(days);
  } else {
    $("#noofdays").val(0);
  }
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

<label>Start Date
 <input type="date" id="startdate" value="2019-03-03"/>
</label>

<label>End Date
 <input type="date" id="enddate" value="2019-03-06"/>
</label>

<label>N. of days
 <output id="noofdays"/>
</label>

答案 1 :(得分:10)

为此,您不应搜索这些日期之间的所有日期!

这并不复杂,看一些明显的假设:

  1. 所有完整周都有7天。

  2. 其中2个是周末日。

  3. 其中5个是营业日。

  4. 明显的结论:

    1. 看看所有的日子都是时间的流逝。

    2. 检查周末的哪一天是整周都没时间了。

    3. 没有繁琐的解释..让我展示代码:

      function getBusinessDateCount (startDate, endDate) {
          var elapsed, daysBeforeFirstSaturday, daysAfterLastSunday;
          var ifThen = function (a, b, c) {
              return a == b ? c : a;
          };
      
          elapsed = endDate - startDate;
          elapsed /= 86400000;
      
          daysBeforeFirstSunday = (7 - startDate.getDay()) % 7;
          daysAfterLastSunday = endDate.getDay();
      
          elapsed -= (daysBeforeFirstSunday + daysAfterLastSunday);
          elapsed = (elapsed / 7) * 5;
          elapsed += ifThen(daysBeforeFirstSunday - 1, -1, 0) + ifThen(daysAfterLastSunday, 6, 5);
      
          return Math.ceil(elapsed);
      }
      
      
      var date1 = new Date(1999, 12, 31);
      var date2 = new Date(); // now
      
      print( getBusinessDateCount(date1, date2) );
      

      您可以使用任何日期自行测试。

      我只想注意2000年到2015年之间的this code ONLY consumed 0.43 sec ...它比其他一些代码快得多。

      希望它有所帮助...

      很好的编码!!

答案 2 :(得分:9)

我就是这样做的

function getDays(d1, d2) {
    var one_day=1000*60*60*24;
    var d1_days = parseInt(d1.getTime()/one_day) - 1;
    var d2_days = parseInt(d2.getTime()/one_day);
    var days = (d2_days - d1_days);
    var weeks = (d2_days - d1_days) / 7;
    var day1 = d1.getDay();
    var day2 = d2.getDay();
    if (day1 == 0) {
        days--;
    } else if (day1 == 6) {
        days-=2;
    }
    if (day2 == 0) {
       days-=2;
    } else if (day2 == 6) {
       days--;
    }
    days -= parseInt(weeks) * 2;
    alert(days);
}

getDays(new Date("June 8, 2004"),new Date("February 6, 2010"));

修改
澄清我对@keenebec的评论...... 该解决方案可以很好地适用于小日期差异,并且易于理解。但是在6年的时间里采取“短暂”的东西,你可以看到速度上的显着差异。

http://jsfiddle.net/aSvxv/

我包含了所有3个答案,原来的答案确实是最快的,但并不是很多,而且对于我来说,执行几微秒的处理对于可读性来说有点微不足道。

答案 3 :(得分:1)

这看起来对我来说太过分了。我宁愿让电脑做重物 - //

Date.bizdays= function(d1, d2){
    var bd= 0, dd, incr=d1.getDate();
    while(d1<d2){
        d1.setDate(++incr);
        dd= d1.getDay();
        if(dd%6)++bd;
    }
    return bd;
}

//test

var day1= new Date(2010, 7, 11), day2= new Date(2010, 7, 31);

alert(Date.bizdays(day1, day2))

答案 4 :(得分:1)

了解方式。

  1. 实际天数= 14
  2. 实际天数
  3. 周= 14/7 = 2
  4. 每周周末= 2
  5. 周末总数= 2天*周
  6. 所以应用这个,

     $('#EndDate').on('change', function () {
                var start = $('#StartDate').datepicker('getDate');
                var end = $('#EndDate').datepicker('getDate');
                if (start < end) {
                    var days = (end - start) / 1000 / 60 / 60 / 24;
    
                    var Weeks=Math.round(days)/7;
    
                    var totalWeekends=Math.round(Weeks)*2;
    
                    var puredays=Math.round(days)-totalWeekends;
    
                    $('#days').text(Math.round(puredays) + "Working Days");
    
    
                }
                else {
    alert("");
    }
    

    谢谢!

答案 5 :(得分:0)

我使用此代码。请注意,该功能来自date.js和businessday js(感谢Garis Suero)。开课日期11-08-2010结束日期16-08-2010将产生4天假。

<script type="text/javascript">

    $("#startdate, #enddate").change(function() {       

    var d1 = $("#startdate").val();
    var d2 = $("#enddate").val();

            var minutes = 1000*60;
            var hours = minutes*60;
            var day = hours*24;

            var startdate1 = getDateFromFormat(d1, "d-m-y");
            var enddate1 = getDateFromFormat(d2, "d-m-y");

            var days = calcBusinessDays(new Date(startdate1),new Date(enddate1));             

    if(days>0)
    { $("#noofdays").val(days);}
    else
    { $("#noofdays").val(0);}


    });

    </script>

答案 6 :(得分:0)

我做了什么

function calcbusinessdays()
{
    for(var c=0,e=0,d=new Date($("#startdate").val()),a=(new Date($("#enddate").val())-d)/864E5;0<=a;a--)
    {
        var b=new Date(d);
        b.setDate(b.getDate()+a);
        1==Math.ceil(b.getDay()%6/6)?c++:e++
    }
    $("#noofdays").html(c)
};

c是工作日,e是周末

答案 7 :(得分:0)

function addDays(date, days) {
    var result = new Date(date);
    result.setDate(result.getDate() + days);
    return result;
}
 var currentDate;
                            selectFlixbleDates = [];
                            var monToSatDateFilter=[];
                            currentDate=new Date(date);
                            while(currentDate){
                                console.log("currentDate"+currentDate);
                                if(new Date(currentDate).getDay()!=0){
                                    selectFlixbleDates.push(currentDate)
                                }
                                if(selectFlixbleDates.length==$scope.numberOfDatePick)
                                {

                                    break;
                                }
                                currentDate=addDays(currentDate,1);

                            }
                            for (var i = 0; i < selectFlixbleDates.length; i++) {

                                //  console.log(between[i]);
                                monToSatDateFilter.push((selectFlixbleDates[i].getMonth() + 1) + '/' + selectFlixbleDates[i].getDate() + '/' + selectFlixbleDates[i].getFullYear());

                            }
                            var endDate=monToSatDateFilter.slice(-1).pop();
                            var space =monToSatDateFilter.join(', ');
                            var sdfs= document.getElementById("maxPicks").value =space;
                            $scope.$apply(function() {
                                $scope.orderEndDate=monToSatDateFilter.slice(-1).pop()
                                $scope.orderStartDate=monToSatDateFilter[0];
                            });
                            document.getElementById("startDateEndDate").innerHTML =$scope.orderStartDate+ ' TO ' +$scope.orderEndDate
                        }  

答案 8 :(得分:0)

重要提示:如果开始日期(有时是结束日期)是星期六或星期日,则此处的大多数答案实际上并不起作用。我接受了接受的回复并对其进行了修改,以便现在可以解决此问题:

    var dateDiff;
    if (dateTo < dateFrom) return -1; // error code if dates transposed
    var dateFromDayOrig = dateFrom.getDay(); // day of week
    var dateToDayOrig = dateTo.getDay();
    var dateFromDay = (dateFromDayOrig == 0) ? 7 : dateFromDayOrig; // change Sunday from 0 to 7
    var dateToDay = (dateToDayOrig == 0) ? 7 : dateToDayOrig;
    dateFromDay = (dateFromDay > 5) ? 5 : dateFromDay; // only count weekdays
    dateToDay = (dateToDay > 5) ? 5 : dateToDay;

    // calculate differnece in weeks (1000mS * 60sec * 60min * 24hrs * 7 days = 604800000)
    var weekDifference = Math.floor((dateTo.getTime() - dateFrom.getTime()) / 604800000);

    if (dateFromDay <= dateToDay) {
        dateDiff = (weekDifference * 5) + (dateToDay - dateFromDay);
    } else {
        dateDiff = ((weekDifference + 1) * 5) - (dateFromDay - dateToDay);
    }

    // fix: remove one day if it's saturday or sunday
    if (dateFromDayOrig >= 6 || dateFromDayOrig == 0) {
    dateDiff--;
    }

    return (dateDiff + 1); // add 1 because dates are inclusive

答案 9 :(得分:0)

被标记为解决方案的响应似乎没有什么问题。

  • 如果我选择开始日期为06/11/2015,则setFullYear()语句返回的值不正确。因此,可以将startDate1和endDate1直接传递给该函数。

  • 如果开始日期是星期六或星期日,则代码仍将其(iWeekday1)计为5天

  • 如果结束日期是星期六或星期日,则代码仍会将其(iWeekday2)计为5天。但是这5天已经计入iweeks计算中。
    所以不是
    iWeekday1 =(iWeekday1> 5)? 5:iWeekday1; //仅计算工作日
    iWeekday2 =(iWeekday2> 5)? 5:iWeekday2;

    应该是
    iWeekday1 =(iWeekday1> 5)? 0 :iWeekday1; //仅计算工作日
    iWeekday2 =(iWeekday2> 5)? 0 :iWeekday2;

  • 当开始日期和结束日期相同时(例如日期可能在同一天),应该执行最后一个IF条件
    如果(iWeekday1 << strong> =
    iWeekday2)

  • 如果两天都是周末,则可以调整的条件可以删除
    iDateDiff-= iAdjust

  • 最后,仅当开始日期和结束日期在工作日内时,才应执行+1。目前,这两种情况都在增加。
    return(iDateDiff +1); //添加条件仅在两天都是工作日时适用

-无法对此答案发表评论,因为我没有这样的声誉:)

答案 10 :(得分:0)

我已经使用Angular框架和Moment.js库来实现该解决方案。 我的解决方案涵盖了所有情况。

this.daysInBetween = this.endMoment.diff(this.startMoment, 'days') + 1;
this.weeksInBetween = this.endMoment.diff(this.startMoment, 'weeks');
this.weekDays = this.daysInBetween - (this.weeksInBetween * 2);

if ( (this.startMoment.day() === 0 && this.endMoment.day() === 6) ||
 (this.startMoment.day() > this.endMoment.day()) ) {
  // IF ONE WEEKEND WAS MISSED
  this.weekDays-=2;
} else if ( this.startMoment.day() <= this.endMoment.day() &&
( this.startMoment.day() === 0 || this.startMoment.day() === 6 ||
  this.endMoment.day() === 0 || this.endMoment.day() === 6) ) {
  // IF EITHER OF DAYS WAS A WEEKEND
  this.weekDays--;
}

现场演示: Calculate number of weekdays

我目前正在写博客,以介绍我​​的处理方法 具体问题。我将在评论中发布指向博客的链接。