JavaScript 中两个日期之间的月份差异

发布于 2024-08-26 18:19:07 字数 70 浏览 3 评论 0原文

如何计算 JavaScript 中两个 Date() 对象的差异,同时只返回差异的月数?

任何帮助都会很棒:)

How would I work out the difference for two Date() objects in JavaScript, while only return the number of months in the difference?

Any help would be great :)

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(29

回心转意 2024-09-02 18:19:08

以月份为单位考虑每个日期,然后减去以找出差异。

var past_date = new Date('11/1/2014');
var current_date = new Date();

var difference = (current_date.getFullYear()*12 + current_date.getMonth()) - (past_date.getFullYear()*12 + past_date.getMonth());

这将为您提供两个日期之间的月份差异,忽略天数。

Consider each date in terms of months, then subtract to find the difference.

var past_date = new Date('11/1/2014');
var current_date = new Date();

var difference = (current_date.getFullYear()*12 + current_date.getMonth()) - (past_date.getFullYear()*12 + past_date.getMonth());

This will get you the difference of months between the two dates, ignoring the days.

骄傲 2024-09-02 18:19:08

计算两个日期之间的差异,包括月份(天)的一部分。


var difference = (date2.getDate() - date1.getDate()) / 30 +
    date2.getMonth() - date1.getMonth() +
    (12 * (date2.getFullYear() - date1.getFullYear()));

例如:
日期1:2015年9月24日(2015年9月24日)
日期2:2015年11月9日(2015年11月9日)
差异:2.5(月)

Calculate the difference between two dates include fraction of month (days).


var difference = (date2.getDate() - date1.getDate()) / 30 +
    date2.getMonth() - date1.getMonth() +
    (12 * (date2.getFullYear() - date1.getFullYear()));

For example:
date1: 24/09/2015 (24th Sept 2015)
date2: 09/11/2015 (9th Nov 2015)
the difference: 2.5 (months)

默嘫て 2024-09-02 18:19:08

有两种方法,数学方法和数学方法。很快,但会受到日历中变幻莫测的影响,或者迭代和迭代。缓慢,但可以处理所有奇怪的情况(或者至少将它们委托给经过良好测试的库处理)。

如果您迭代日历,则将开始日期增加一个月并增加一个月。看看我们是否超过了结束日期。这将异常处理委托给内置的 Date() 类,但如果您对大量日期执行此操作,速度可能会很慢。詹姆斯的回答就采用了这种方法。尽管我不喜欢这个想法,但我认为这是“最安全”的方法,如果您只进行一次计算,那么性能差异实际上可以忽略不计。我们倾向于尝试过度优化只执行一次的任务。

现在,如果您要在数据集上计算此函数,您可能不想在每一行上运行该函数(或者上帝保佑,每条记录运行多次)。在这种情况下,您可以使用这里几乎任何其他答案,除了接受的答案,这是错误的(new Date()new Date 之间的差异() 是 -1)?

这是我尝试的一种数学快速方法,它解释了不同的月份长度和闰年。如果您要将其应用到数据集(一遍又一遍地进行此计算),您实际上应该只使用这样的函数。如果您只需要执行一次,请使用上面 James 的迭代方法,因为您将处理所有(许多)异常委托给 Date() 对象。

function diffInMonths(from, to){
    var months = to.getMonth() - from.getMonth() + (12 * (to.getFullYear() - from.getFullYear()));

    if(to.getDate() < from.getDate()){
        var newFrom = new Date(to.getFullYear(),to.getMonth(),from.getDate());
        if (to < newFrom  && to.getMonth() == newFrom.getMonth() && to.getYear() %4 != 0){
            months--;
        }
    }

    return months;
}

There are two approaches, mathematical & quick, but subject to vagaries in the calendar, or iterative & slow, but handles all the oddities (or at least delegates handling them to a well-tested library).

If you iterate through the calendar, incrementing the start date by one month & seeing if we pass the end date. This delegates anomaly-handling to the built-in Date() classes, but could be slow IF you're doing this for a large number of dates. James' answer takes this approach. As much as I dislike the idea, I think this is the "safest" approach, and if you're only doing one calculation, the performance difference really is negligible. We tend to try to over-optimize tasks which will only be performed once.

Now, if you're calculating this function on a dataset, you probably don't want to run that function on each row (or god forbid, multiple times per record). In that case, you can use almost any of the other answers here except the accepted answer, which is just wrong (difference between new Date() and new Date() is -1)?

Here's my stab at a mathematical-and-quick approach, which accounts for differing month lengths and leap years. You really should only use a function like this if you'll be applying this to a dataset (doing this calculation over & over). If you just need to do it once, use James' iterative approach above, as you're delegating handling all the (many) exceptions to the Date() object.

function diffInMonths(from, to){
    var months = to.getMonth() - from.getMonth() + (12 * (to.getFullYear() - from.getFullYear()));

    if(to.getDate() < from.getDate()){
        var newFrom = new Date(to.getFullYear(),to.getMonth(),from.getDate());
        if (to < newFrom  && to.getMonth() == newFrom.getMonth() && to.getYear() %4 != 0){
            months--;
        }
    }

    return months;
}
埋葬我深情 2024-09-02 18:19:08

日期和日期的月数时间并不重要

在这种情况下,我不关心完整月份、部分月份、一个月有多长等。我只需要知道月份数。 一个相关的现实案例是每个月都有一份报告到期,我需要知道应该有多少份报告。

示例:

  • 一月 = 1 个月
  • 1 月 - 2 月 = 2 个月
  • 11 月 - 1 月 = 3 个月

这是一个详细的代码示例,用于显示数字的去向。

让我们采用 2 个时间戳,应为 4 个月

  • 2019 年 11 月 13 日的时间戳:1573621200000
  • 2020 年 2 月 20 日的时间戳:1582261140000

可能与您提取的时区/时间略有不同。日、分、秒并不重要,可以包含在时间戳中,但我们在实际计算中会忽略它。

步骤 1:将时间戳转换为 JavaScript 日期

let dateRangeStartConverted = new Date(1573621200000);
let dateRangeEndConverted = new Date(1582261140000);

步骤 2:获取整数值月/年

let startingMonth = dateRangeStartConverted.getMonth();
let startingYear = dateRangeStartConverted.getFullYear();
let endingMonth = dateRangeEndConverted.getMonth();
let endingYear = dateRangeEndConverted.getFullYear();

这给了我们

  • 开始月份:11
  • 开始年份:2019
  • 结束月份:2
  • 结束年份:2020

第3步:添加(12 * (endYear - startYear)) + 1 到结束月份。

  • 这使得我们的起始月份保持在 11
  • 这使得我们的结束月份等于 15 2 + (12 * (2020 - 2019)) + 1 = 15

步骤 4:减去月份

15 - 11 = 4;我们得到了 4 个月的结果。

29 个月示例 示例

2019 年 11 月至 2022 年 3 月为 29 个月。如果将它们放入 Excel 电子表格中,您将看到 29 行。

  • 我们的起始月份是 11
  • 我们的结束月份是 40 3 + (12 * (2022-2019)) + 1

40 - 11 = 29

Number Of Months When Day & Time Doesn't Matter

In this case, I'm not concerned with full months, part months, how long a month is, etc. I just need to know the number of months. A relevant real world case would be where a report is due every month, and I need to know how many reports there should be.

Example:

  • January = 1 month
  • January - February = 2 months
  • November - January = 3 months

This is an elaborated code example to show where the numbers are going.

Let's take 2 timestamps that should result in 4 months

  • November 13, 2019's timestamp: 1573621200000
  • February 20, 2020's timestamp: 1582261140000

May be slightly different with your timezone / time pulled. The day, minutes, and seconds don't matter and can be included in the timestamp, but we will disregard it with our actual calculation.

Step 1: convert the timestamp to a JavaScript date

let dateRangeStartConverted = new Date(1573621200000);
let dateRangeEndConverted = new Date(1582261140000);

Step 2: get integer values for the months / years

let startingMonth = dateRangeStartConverted.getMonth();
let startingYear = dateRangeStartConverted.getFullYear();
let endingMonth = dateRangeEndConverted.getMonth();
let endingYear = dateRangeEndConverted.getFullYear();

This gives us

  • Starting month: 11
  • Starting Year: 2019
  • Ending month: 2
  • Ending Year: 2020

Step 3: Add (12 * (endYear - startYear)) + 1 to the ending month.

  • This makes our starting month stay at 11
  • This makes our ending month equal 15 2 + (12 * (2020 - 2019)) + 1 = 15

Step 4: Subtract the months

15 - 11 = 4; we get our 4 month result.

29 Month Example Example

November 2019 through March 2022 is 29 months. If you put these into an excel spreadsheet, you will see 29 rows.

  • Our starting month is 11
  • Our ending month is 40 3 + (12 * (2022-2019)) + 1

40 - 11 = 29

难以启齿的温柔 2024-09-02 18:19:08

这里就可以了其他循环较少的方法:

calculateTotalMonthsDifference = function(firstDate, secondDate) {
        var fm = firstDate.getMonth();
        var fy = firstDate.getFullYear();
        var sm = secondDate.getMonth();
        var sy = secondDate.getFullYear();
        var months = Math.abs(((fy - sy) * 12) + fm - sm);
        var firstBefore = firstDate > secondDate;
        firstDate.setFullYear(sy);
        firstDate.setMonth(sm);
        firstBefore ? firstDate < secondDate ? months-- : "" : secondDate < firstDate ? months-- : "";
        return months;
}

Here you go other approach with less looping:

calculateTotalMonthsDifference = function(firstDate, secondDate) {
        var fm = firstDate.getMonth();
        var fy = firstDate.getFullYear();
        var sm = secondDate.getMonth();
        var sy = secondDate.getFullYear();
        var months = Math.abs(((fy - sy) * 12) + fm - sm);
        var firstBefore = firstDate > secondDate;
        firstDate.setFullYear(sy);
        firstDate.setMonth(sm);
        firstBefore ? firstDate < secondDate ? months-- : "" : secondDate < firstDate ? months-- : "";
        return months;
}
千柳 2024-09-02 18:19:08

这应该可以正常工作:

function monthDiff(d1, d2) {
    var months;
    months = (d2.getFullYear() - d1.getFullYear()) * 12;
    months += d2.getMonth() - d1.getMonth();
    return months;
}

This should work fine:

function monthDiff(d1, d2) {
    var months;
    months = (d2.getFullYear() - d1.getFullYear()) * 12;
    months += d2.getMonth() - d1.getMonth();
    return months;
}
凡间太子 2024-09-02 18:19:08
function calcualteMonthYr(){
    var fromDate =new Date($('#txtDurationFrom2').val()); //date picker (text fields)
    var toDate = new Date($('#txtDurationTo2').val());

var months=0;
        months = (toDate.getFullYear() - fromDate.getFullYear()) * 12;
        months -= fromDate.getMonth();
        months += toDate.getMonth();
            if (toDate.getDate() < fromDate.getDate()){
                months--;
            }
    $('#txtTimePeriod2').val(months);
}
function calcualteMonthYr(){
    var fromDate =new Date($('#txtDurationFrom2').val()); //date picker (text fields)
    var toDate = new Date($('#txtDurationTo2').val());

var months=0;
        months = (toDate.getFullYear() - fromDate.getFullYear()) * 12;
        months -= fromDate.getMonth();
        months += toDate.getMonth();
            if (toDate.getDate() < fromDate.getDate()){
                months--;
            }
    $('#txtTimePeriod2').val(months);
}
恍梦境° 2024-09-02 18:19:08

以下代码还考虑了部分月份的天数,返回两个日期之间的完整月份。

var monthDiff = function(d1, d2) {
  if( d2 < d1 ) { 
    var dTmp = d2;
    d2 = d1;
    d1 = dTmp;
  }

  var months = (d2.getFullYear() - d1.getFullYear()) * 12;
  months -= d1.getMonth() + 1;
  months += d2.getMonth();

  if( d1.getDate() <= d2.getDate() ) months += 1;

  return months;
}

monthDiff(new Date(2015, 01, 20), new Date(2015, 02, 20))
> 1

monthDiff(new Date(2015, 01, 20), new Date(2015, 02, 19))
> 0

monthDiff(new Date(2015, 01, 20), new Date(2015, 01, 22))
> 0

Following code returns full months between two dates by taking nr of days of partial months into account as well.

var monthDiff = function(d1, d2) {
  if( d2 < d1 ) { 
    var dTmp = d2;
    d2 = d1;
    d1 = dTmp;
  }

  var months = (d2.getFullYear() - d1.getFullYear()) * 12;
  months -= d1.getMonth() + 1;
  months += d2.getMonth();

  if( d1.getDate() <= d2.getDate() ) months += 1;

  return months;
}

monthDiff(new Date(2015, 01, 20), new Date(2015, 02, 20))
> 1

monthDiff(new Date(2015, 01, 20), new Date(2015, 02, 19))
> 0

monthDiff(new Date(2015, 01, 20), new Date(2015, 01, 22))
> 0
來不及說愛妳 2024-09-02 18:19:08
function monthDiff(d1, d2) {
var months, d1day, d2day, d1new, d2new, diffdate,d2month,d2year,d1maxday,d2maxday;
months = (d2.getFullYear() - d1.getFullYear()) * 12;
months -= d1.getMonth() + 1;
months += d2.getMonth();
months = (months <= 0 ? 0 : months);
d1day = d1.getDate();
d2day = d2.getDate();
if(d1day > d2day)
{
    d2month = d2.getMonth();
    d2year = d2.getFullYear();
    d1new = new Date(d2year, d2month-1, d1day,0,0,0,0);
    var timeDiff = Math.abs(d2.getTime() - d1new.getTime());
          diffdate = Math.abs(Math.ceil(timeDiff / (1000 * 3600 * 24))); 
    d1new = new Date(d2year, d2month, 1,0,0,0,0);
    d1new.setDate(d1new.getDate()-1);
    d1maxday = d1new.getDate();
    months += diffdate / d1maxday;
}
else
{
      if(!(d1.getMonth() == d2.getMonth() && d1.getFullYear() == d2.getFullYear()))
    {
        months += 1;
    }
    diffdate = d2day - d1day + 1;
    d2month = d2.getMonth();
    d2year = d2.getFullYear();
    d2new = new Date(d2year, d2month + 1, 1, 0, 0, 0, 0);
    d2new.setDate(d2new.getDate()-1);
    d2maxday = d2new.getDate();
    months += diffdate / d2maxday;
}

return months;

}

function monthDiff(d1, d2) {
var months, d1day, d2day, d1new, d2new, diffdate,d2month,d2year,d1maxday,d2maxday;
months = (d2.getFullYear() - d1.getFullYear()) * 12;
months -= d1.getMonth() + 1;
months += d2.getMonth();
months = (months <= 0 ? 0 : months);
d1day = d1.getDate();
d2day = d2.getDate();
if(d1day > d2day)
{
    d2month = d2.getMonth();
    d2year = d2.getFullYear();
    d1new = new Date(d2year, d2month-1, d1day,0,0,0,0);
    var timeDiff = Math.abs(d2.getTime() - d1new.getTime());
          diffdate = Math.abs(Math.ceil(timeDiff / (1000 * 3600 * 24))); 
    d1new = new Date(d2year, d2month, 1,0,0,0,0);
    d1new.setDate(d1new.getDate()-1);
    d1maxday = d1new.getDate();
    months += diffdate / d1maxday;
}
else
{
      if(!(d1.getMonth() == d2.getMonth() && d1.getFullYear() == d2.getFullYear()))
    {
        months += 1;
    }
    diffdate = d2day - d1day + 1;
    d2month = d2.getMonth();
    d2year = d2.getFullYear();
    d2new = new Date(d2year, d2month + 1, 1, 0, 0, 0, 0);
    d2new.setDate(d2new.getDate()-1);
    d2maxday = d2new.getDate();
    months += diffdate / d2maxday;
}

return months;

}

嘴硬脾气大 2024-09-02 18:19:08

以下逻辑将获取几个月的差异

(endDate.getFullYear()*12+endDate.getMonth())-(startDate.getFullYear()*12+startDate.getMonth())

below logic will fetch difference in months

(endDate.getFullYear()*12+endDate.getMonth())-(startDate.getFullYear()*12+startDate.getMonth())
终陌 2024-09-02 18:19:08
function monthDiff(date1, date2, countDays) {

  countDays = (typeof countDays !== 'undefined') ?  countDays : false;

  if (!date1 || !date2) {
    return 0;
  }

  let bigDate = date1;
  let smallDate = date2;

  if (date1 < date2) {
    bigDate = date2;
    smallDate = date1;
  }

  let monthsCount = (bigDate.getFullYear() - smallDate.getFullYear()) * 12 + (bigDate.getMonth() - smallDate.getMonth());

  if (countDays && bigDate.getDate() < smallDate.getDate()) {
    --monthsCount;
  }

  return monthsCount;
}
function monthDiff(date1, date2, countDays) {

  countDays = (typeof countDays !== 'undefined') ?  countDays : false;

  if (!date1 || !date2) {
    return 0;
  }

  let bigDate = date1;
  let smallDate = date2;

  if (date1 < date2) {
    bigDate = date2;
    smallDate = date1;
  }

  let monthsCount = (bigDate.getFullYear() - smallDate.getFullYear()) * 12 + (bigDate.getMonth() - smallDate.getMonth());

  if (countDays && bigDate.getDate() < smallDate.getDate()) {
    --monthsCount;
  }

  return monthsCount;
}
入画浅相思 2024-09-02 18:19:08

这是我能找到的最简单的解决方案。这将直接返回月份数。虽然,它总是给出绝对值。

new Date(new Date(d2) - new Date(d1)).getMonth();

对于非绝对值,可以使用以下解决方案:

function diff_months(startDate, endDate) {
  let diff = new Date( new Date(endDate)  - new Date(startDate) ).getMonth();
  return endDate >= startDate ? diff : -diff;
}

This is the simplest solution I could find. This will directly return the number of months. Although, it always gives an absolute value.

new Date(new Date(d2) - new Date(d1)).getMonth();

For non-absolute values, you can use the following solution:

function diff_months(startDate, endDate) {
  let diff = new Date( new Date(endDate)  - new Date(startDate) ).getMonth();
  return endDate >= startDate ? diff : -diff;
}
忘东忘西忘不掉你 2024-09-02 18:19:08

看看我用的是什么:

function monthDiff() {
    var startdate = Date.parseExact($("#startingDate").val(), "dd/MM/yyyy");
    var enddate = Date.parseExact($("#endingDate").val(), "dd/MM/yyyy");
    var months = 0;
    while (startdate < enddate) {
        if (startdate.getMonth() === 1 && startdate.getDate() === 28) {
            months++;
            startdate.addMonths(1);
            startdate.addDays(2);
        } else {
            months++;
            startdate.addMonths(1);
        }
    }
    return months;
}

See what I use:

function monthDiff() {
    var startdate = Date.parseExact($("#startingDate").val(), "dd/MM/yyyy");
    var enddate = Date.parseExact($("#endingDate").val(), "dd/MM/yyyy");
    var months = 0;
    while (startdate < enddate) {
        if (startdate.getMonth() === 1 && startdate.getDate() === 28) {
            months++;
            startdate.addMonths(1);
            startdate.addDays(2);
        } else {
            months++;
            startdate.addMonths(1);
        }
    }
    return months;
}
七色彩虹 2024-09-02 18:19:08

它还计算天数并将其转换为月。

function monthDiff(d1, d2) {
    var months;
    months = (d2.getFullYear() - d1.getFullYear()) * 12;   //calculates months between two years
    months -= d1.getMonth() + 1; 
    months += d2.getMonth();  //calculates number of complete months between two months
    day1 = 30-d1.getDate();  
    day2 = day1 + d2.getDate();
    months += parseInt(day2/30);  //calculates no of complete months lie between two dates
    return months <= 0 ? 0 : months;
}

monthDiff(
    new Date(2017, 8, 8), // Aug 8th, 2017    (d1)
    new Date(2017, 12, 12)  // Dec 12th, 2017   (d2)
);
//return value will be 4 months 

It also counts the days and convert them in months.

function monthDiff(d1, d2) {
    var months;
    months = (d2.getFullYear() - d1.getFullYear()) * 12;   //calculates months between two years
    months -= d1.getMonth() + 1; 
    months += d2.getMonth();  //calculates number of complete months between two months
    day1 = 30-d1.getDate();  
    day2 = day1 + d2.getDate();
    months += parseInt(day2/30);  //calculates no of complete months lie between two dates
    return months <= 0 ? 0 : months;
}

monthDiff(
    new Date(2017, 8, 8), // Aug 8th, 2017    (d1)
    new Date(2017, 12, 12)  // Dec 12th, 2017   (d2)
);
//return value will be 4 months 
悲凉≈ 2024-09-02 18:19:08
getMonthDiff(d1, d2) {
    var year1 = dt1.getFullYear();
    var year2 = dt2.getFullYear();
    var month1 = dt1.getMonth();
    var month2 = dt2.getMonth();
    var day1 = dt1.getDate();
    var day2 = dt2.getDate();
    var months = month2 - month1;
    var years = year2 -year1
    days = day2 - day1;
    if (days < 0) {
        months -= 1;
    }
    if (months < 0) {
        months += 12;
    }
    return months + years*!2;
}
getMonthDiff(d1, d2) {
    var year1 = dt1.getFullYear();
    var year2 = dt2.getFullYear();
    var month1 = dt1.getMonth();
    var month2 = dt2.getMonth();
    var day1 = dt1.getDate();
    var day2 = dt2.getDate();
    var months = month2 - month1;
    var years = year2 -year1
    days = day2 - day1;
    if (days < 0) {
        months -= 1;
    }
    if (months < 0) {
        months += 12;
    }
    return months + years*!2;
}
扮仙女 2024-09-02 18:19:08

任何值都会与其绝对值一起返回。

function differenceInMonths(firstDate, secondDate) {
    if (firstDate > secondDate) [firstDate, secondDate] = [secondDate, firstDate];
    let diffMonths = (secondDate.getFullYear() - firstDate.getFullYear()) * 12;
    diffMonths -= firstDate.getMonth();
    diffMonths += secondDate.getMonth();
    return diffMonths;
}
 

Any value is returned along with its absolute value.

function differenceInMonths(firstDate, secondDate) {
    if (firstDate > secondDate) [firstDate, secondDate] = [secondDate, firstDate];
    let diffMonths = (secondDate.getFullYear() - firstDate.getFullYear()) * 12;
    diffMonths -= firstDate.getMonth();
    diffMonths += secondDate.getMonth();
    return diffMonths;
}
 
面犯桃花 2024-09-02 18:19:08

以下代码片段帮助我找到两个日期之间的月份

查找两个日期之间的月份数 JS

两个日期之间的月份 JS

代码片段

function diff_months_count(startDate, endDate) {
    var months;
    var d1 = new Date(startDate);
    var d2 = new Date(endDate);
    months = (d2.getFullYear() - d1.getFullYear()) * 12;
    months -= d1.getMonth();
    months += d2.getMonth();
    return months <= 0 ? 0 : months;
}

The following code snippet helped me to find months between two dates

Find Months Count Between two dates JS

Months Between two dates JS

Code Snippet

function diff_months_count(startDate, endDate) {
    var months;
    var d1 = new Date(startDate);
    var d2 = new Date(endDate);
    months = (d2.getFullYear() - d1.getFullYear()) * 12;
    months -= d1.getMonth();
    months += d2.getMonth();
    return months <= 0 ? 0 : months;
}
三五鸿雁 2024-09-02 18:19:08

#这是我编写的一段很好的代码,用于获取天数和月数
从给定日期开始

[1]:jsfiddle 链接

/**
 * Date a end day
 * Date b start day
 * @param DateA Date @param DateB Date
 * @returns Date difference
 */
function getDateDifference(dateA, DateB, type = 'month') {
  const END_DAY = new Date(dateA)
  const START_DAY = new Date(DateB)
  let calculatedDateBy
  let returnDateDiff
  if (type === 'month') {
    const startMonth = START_DAY.getMonth()
    const endMonth = END_DAY.getMonth()
    calculatedDateBy = startMonth - endMonth
    returnDateDiff = Math.abs(
      calculatedDateBy + 12 * (START_DAY.getFullYear() - END_DAY.getFullYear())
    )
  } else {
    calculatedDateBy = Math.abs(START_DAY - END_DAY)
    returnDateDiff = Math.ceil(calculatedDateBy / (1000 * 60 * 60 * 24))
  }
  const out = document.getElementById('output')
  out.innerText = returnDateDiff
  return returnDateDiff
}
// Gets number of days from given dates
/* getDateDifference('2022-03-31','2022-04-08','day') */
// Get number of months from given dates
getDateDifference('2021-12-02','2022-04-08','month')
<div id="output"> </div>

#Here is a nice piece of code i wrote for getting number of days and months
from given dates

[1]: jsfiddle link

/**
 * Date a end day
 * Date b start day
 * @param DateA Date @param DateB Date
 * @returns Date difference
 */
function getDateDifference(dateA, DateB, type = 'month') {
  const END_DAY = new Date(dateA)
  const START_DAY = new Date(DateB)
  let calculatedDateBy
  let returnDateDiff
  if (type === 'month') {
    const startMonth = START_DAY.getMonth()
    const endMonth = END_DAY.getMonth()
    calculatedDateBy = startMonth - endMonth
    returnDateDiff = Math.abs(
      calculatedDateBy + 12 * (START_DAY.getFullYear() - END_DAY.getFullYear())
    )
  } else {
    calculatedDateBy = Math.abs(START_DAY - END_DAY)
    returnDateDiff = Math.ceil(calculatedDateBy / (1000 * 60 * 60 * 24))
  }
  const out = document.getElementById('output')
  out.innerText = returnDateDiff
  return returnDateDiff
}
// Gets number of days from given dates
/* getDateDifference('2022-03-31','2022-04-08','day') */
// Get number of months from given dates
getDateDifference('2021-12-02','2022-04-08','month')
<div id="output"> </div>

守不住的情 2024-09-02 18:19:08
anyVar = (((DisplayTo.getFullYear() * 12) + DisplayTo.getMonth()) - ((DisplayFrom.getFullYear() * 12) + DisplayFrom.getMonth()));
anyVar = (((DisplayTo.getFullYear() * 12) + DisplayTo.getMonth()) - ((DisplayFrom.getFullYear() * 12) + DisplayFrom.getMonth()));
一向肩并 2024-09-02 18:19:08

一种方法是编写一个使用 JODA 库

http 的简单 Java Web 服务 (REST/JSON) ://joda-time.sourceforge.net/faq.html#datediff

计算两个日期之间的差异并从 JavaScript 调用该服务。

这假设您的后端是 Java 语言。

One approach would be to write a simple Java Web Service (REST/JSON) that uses JODA library

http://joda-time.sourceforge.net/faq.html#datediff

to calculate difference between two dates and call that service from javascript.

This assumes your back end is in Java.

隔岸观火 2024-09-02 18:19:07

“差异月数”的定义有很多解释。 :-)

您可以从 JavaScript 日期对象获取年、月和日。根据您要查找的信息,您可以使用这些信息来计算两个时间点之间相差多少个月。

例如,即兴:

function monthDiff(d1, d2) {
    var months;
    months = (d2.getFullYear() - d1.getFullYear()) * 12;
    months -= d1.getMonth();
    months += d2.getMonth();
    return months <= 0 ? 0 : months;
}

function monthDiff(d1, d2) {
    var months;
    months = (d2.getFullYear() - d1.getFullYear()) * 12;
    months -= d1.getMonth();
    months += d2.getMonth();
    return months <= 0 ? 0 : months;
}

function test(d1, d2) {
    var diff = monthDiff(d1, d2);
    console.log(
        d1.toISOString().substring(0, 10),
        "to",
        d2.toISOString().substring(0, 10),
        ":",
        diff
    );
}

test(
    new Date(2008, 10, 4), // November 4th, 2008
    new Date(2010, 2, 12)  // March 12th, 2010
);
// Result: 16

test(
    new Date(2010, 0, 1),  // January 1st, 2010
    new Date(2010, 2, 12)  // March 12th, 2010
);
// Result: 2

test(
    new Date(2010, 1, 1),  // February 1st, 2010
    new Date(2010, 2, 12)  // March 12th, 2010
);
// Result: 1

(请注意,JavaScript 中的月份值以 0 = 一月开头。)

在上面包含小数月份要复杂得多,因为典型的二月中的三天占该月的比例 (~10.714%) 比八月的三天要大 ( ~9.677%),当然,甚至二月也是一个移动目标,具体取决于它是否是闰年。

还有一些可用于 JavaScript 的日期和时间库,可能会使此类事情变得更容易。


注意:上面原来有一个+1,这里:

months = (d2.getFullYear() - d1.getFullYear()) * 12;
months -= d1.getMonth() + 1;
// −−−−−−−−−−−−−−−−−−−−^^^^
months += d2.getMonth();

那是因为我本来是这么说的:

...这可以找出两个日期之间有多少个完整月份,不计算部分月份(例如,排除每个日期所在的月份)。

我删除它有两个原因:

  1. 事实证明,不计算部分月份并不是很多(大多数?)人想要得到答案的结果,所以我认为我应该将它们分开。

  2. 即使按照这个定义,它也并不总是有效。 :-D(抱歉。)

The definition of "the number of months in the difference" is subject to a lot of interpretation. :-)

You can get the year, month, and day of month from a JavaScript date object. Depending on what information you're looking for, you can use those to figure out how many months are between two points in time.

For instance, off-the-cuff:

function monthDiff(d1, d2) {
    var months;
    months = (d2.getFullYear() - d1.getFullYear()) * 12;
    months -= d1.getMonth();
    months += d2.getMonth();
    return months <= 0 ? 0 : months;
}

function monthDiff(d1, d2) {
    var months;
    months = (d2.getFullYear() - d1.getFullYear()) * 12;
    months -= d1.getMonth();
    months += d2.getMonth();
    return months <= 0 ? 0 : months;
}

function test(d1, d2) {
    var diff = monthDiff(d1, d2);
    console.log(
        d1.toISOString().substring(0, 10),
        "to",
        d2.toISOString().substring(0, 10),
        ":",
        diff
    );
}

test(
    new Date(2008, 10, 4), // November 4th, 2008
    new Date(2010, 2, 12)  // March 12th, 2010
);
// Result: 16

test(
    new Date(2010, 0, 1),  // January 1st, 2010
    new Date(2010, 2, 12)  // March 12th, 2010
);
// Result: 2

test(
    new Date(2010, 1, 1),  // February 1st, 2010
    new Date(2010, 2, 12)  // March 12th, 2010
);
// Result: 1

(Note that month values in JavaScript start with 0 = January.)

Including fractional months in the above is much more complicated, because three days in a typical February is a larger fraction of that month (~10.714%) than three days in August (~9.677%), and of course even February is a moving target depending on whether it's a leap year.

There are also some date and time libraries available for JavaScript that probably make this sort of thing easier.


Note: There used to be a + 1 in the above, here:

months = (d2.getFullYear() - d1.getFullYear()) * 12;
months -= d1.getMonth() + 1;
// −−−−−−−−−−−−−−−−−−−−^^^^
months += d2.getMonth();

That's because originally I said:

...this finds out how many full months lie between two dates, not counting partial months (e.g., excluding the month each date is in).

I've removed it for two reasons:

  1. Not counting partial months turns out not to be what many (most?) people coming to the answer want, so I thought I should separate them out.

  2. It didn't always work even by that definition. :-D (Sorry.)

淡淡の花香 2024-09-02 18:19:07

如果您不考虑该月的哪一天,这是迄今为止更简单的解决方案

function monthDiff(dateFrom, dateTo) {
 return dateTo.getMonth() - dateFrom.getMonth() + 
   (12 * (dateTo.getFullYear() - dateFrom.getFullYear()))
}


//examples
console.log(monthDiff(new Date(2000, 01), new Date(2000, 02))) // 1
console.log(monthDiff(new Date(1999, 02), new Date(2000, 02))) // 12 full year
console.log(monthDiff(new Date(2009, 11), new Date(2010, 0))) // 1

请注意,月份索引是从 0 开始的。这意味着 一月 = 0十二月 = 11

If you do not consider the day of the month, this is by far the simpler solution

function monthDiff(dateFrom, dateTo) {
 return dateTo.getMonth() - dateFrom.getMonth() + 
   (12 * (dateTo.getFullYear() - dateFrom.getFullYear()))
}


//examples
console.log(monthDiff(new Date(2000, 01), new Date(2000, 02))) // 1
console.log(monthDiff(new Date(1999, 02), new Date(2000, 02))) // 12 full year
console.log(monthDiff(new Date(2009, 11), new Date(2010, 0))) // 1

Be aware that month index is 0-based. This means that January = 0 and December = 11.

浮光之海 2024-09-02 18:19:07

这是一个准确提供 2 个日期之间的月数的函数。
默认行为仅计算整月,例如 3 个月加 1 天将导致 3 个月的差异。您可以通过将 roundUpFractionalMonths 参数设置为 true 来防止这种情况发生,因此 3 个月加 1 天的差异将返回为 4 个月。

上面接受的答案(TJ Crowder 的答案)不准确,有时会返回错误的值。

例如,monthDiff(new Date('Jul 01, 2015'), new Date(' Aug 05, 2015')) 返回 0 这显然是错误的。正确的差异是 1 个整月或 2 个月的四舍五入。

这是我写的函数:

function getMonthsBetween(date1,date2,roundUpFractionalMonths)
{
    //Months will be calculated between start and end dates.
    //Make sure start date is less than end date.
    //But remember if the difference should be negative.
    var startDate=date1;
    var endDate=date2;
    var inverse=false;
    if(date1>date2)
    {
        startDate=date2;
        endDate=date1;
        inverse=true;
    }

    //Calculate the differences between the start and end dates
    var yearsDifference=endDate.getFullYear()-startDate.getFullYear();
    var monthsDifference=endDate.getMonth()-startDate.getMonth();
    var daysDifference=endDate.getDate()-startDate.getDate();

    var monthCorrection=0;
    //If roundUpFractionalMonths is true, check if an extra month needs to be added from rounding up.
    //The difference is done by ceiling (round up), e.g. 3 months and 1 day will be 4 months.
    if(roundUpFractionalMonths===true && daysDifference>0)
    {
        monthCorrection=1;
    }
    //If the day difference between the 2 months is negative, the last month is not a whole month.
    else if(roundUpFractionalMonths!==true && daysDifference<0)
    {
        monthCorrection=-1;
    }

    return (inverse?-1:1)*(yearsDifference*12+monthsDifference+monthCorrection);
};

Here's a function that accurately provides the number of months between 2 dates.
The default behavior only counts whole months, e.g. 3 months and 1 day will result in a difference of 3 months. You can prevent this by setting the roundUpFractionalMonths param as true, so a 3 month and 1 day difference will be returned as 4 months.

The accepted answer above (T.J. Crowder's answer) isn't accurate, it returns wrong values sometimes.

For example, monthDiff(new Date('Jul 01, 2015'), new Date('Aug 05, 2015')) returns 0 which is obviously wrong. The correct difference is either 1 whole month or 2 months rounded-up.

Here's the function I wrote:

function getMonthsBetween(date1,date2,roundUpFractionalMonths)
{
    //Months will be calculated between start and end dates.
    //Make sure start date is less than end date.
    //But remember if the difference should be negative.
    var startDate=date1;
    var endDate=date2;
    var inverse=false;
    if(date1>date2)
    {
        startDate=date2;
        endDate=date1;
        inverse=true;
    }

    //Calculate the differences between the start and end dates
    var yearsDifference=endDate.getFullYear()-startDate.getFullYear();
    var monthsDifference=endDate.getMonth()-startDate.getMonth();
    var daysDifference=endDate.getDate()-startDate.getDate();

    var monthCorrection=0;
    //If roundUpFractionalMonths is true, check if an extra month needs to be added from rounding up.
    //The difference is done by ceiling (round up), e.g. 3 months and 1 day will be 4 months.
    if(roundUpFractionalMonths===true && daysDifference>0)
    {
        monthCorrection=1;
    }
    //If the day difference between the 2 months is negative, the last month is not a whole month.
    else if(roundUpFractionalMonths!==true && daysDifference<0)
    {
        monthCorrection=-1;
    }

    return (inverse?-1:1)*(yearsDifference*12+monthsDifference+monthCorrection);
};
溇涏 2024-09-02 18:19:07

有时您可能只想获取两个日期之间的月份数量,完全忽略日期部分。例如,如果您有两个日期 - 2013/06/21 和 2013/10/18 - 并且您只关心 2013/06 和 2013/10 部分,则以下是场景和可能的解决方案:

var date1=new Date(2013,5,21);//Remember, months are 0 based in JS
var date2=new Date(2013,9,18);
var year1=date1.getFullYear();
var year2=date2.getFullYear();
var month1=date1.getMonth();
var month2=date2.getMonth();
if(month1===0){ //Have to take into account
  month1++;
  month2++;
}
var numberOfMonths; 

1.如果您想要仅两个日期之间的月份数,不包括 Month1 和 Month2

numberOfMonths = (year2 - year1) * 12 + (month2 - month1) - 1;

2.如果您想包括任一月份

numberOfMonths = (year2 - year1) * 12 + (month2 - month1);

3.如果您想包括两个月份

numberOfMonths = (year2 - year1) * 12 + (month2 - month1) + 1;

Sometimes you may want to get just the quantity of the months between two dates totally ignoring the day part. So for instance, if you had two dates- 2013/06/21 and 2013/10/18- and you only cared about the 2013/06 and 2013/10 parts, here are the scenarios and possible solutions:

var date1=new Date(2013,5,21);//Remember, months are 0 based in JS
var date2=new Date(2013,9,18);
var year1=date1.getFullYear();
var year2=date2.getFullYear();
var month1=date1.getMonth();
var month2=date2.getMonth();
if(month1===0){ //Have to take into account
  month1++;
  month2++;
}
var numberOfMonths; 

1.If you want just the number of the months between the two dates excluding both month1 and month2

numberOfMonths = (year2 - year1) * 12 + (month2 - month1) - 1;

2.If you want to include either of the months

numberOfMonths = (year2 - year1) * 12 + (month2 - month1);

3.If you want to include both of the months

numberOfMonths = (year2 - year1) * 12 + (month2 - month1) + 1;
慈悲佛祖 2024-09-02 18:19:07

如果您需要计算完整月份,无论月份是 28、29、30 还是 31 天。下面应该可以工作。

var months = to.getMonth() - from.getMonth() 
    + (12 * (to.getFullYear() - from.getFullYear()));

if(to.getDate() < from.getDate()){
    months--;
}
return months;

这是答案的扩展版本 https://stackoverflow.com/a/4312956/1987208 但修复了以下情况:它计算从1月31日到2月1日(1天)的案例1个月。

这将涵盖以下内容;

  • 1月1日至1月31日---> 30天--->将导致 0(逻辑,因为它不是一个完整的月份)
  • 2 月 1 日到 3 月 1 日 ---> 28或29天--->将得到 1(符合逻辑,因为这是一个完整的月份)
  • 2 月 15 日到 3 月 15 日 ---> 28或29天--->将导致 1(自一个月过去以来逻辑)
  • 1 月 31 日至 2 月 1 日 ---> 1天--->将导致 0(显而易见,但帖子中提到的答案会在 1 个月内产生)

If you need to count full months, regardless of the month being 28, 29, 30 or 31 days. Below should work.

var months = to.getMonth() - from.getMonth() 
    + (12 * (to.getFullYear() - from.getFullYear()));

if(to.getDate() < from.getDate()){
    months--;
}
return months;

This is an extended version of the answer https://stackoverflow.com/a/4312956/1987208 but fixes the case where it calculates 1 month for the case from 31st of January to 1st of February (1day).

This will cover the following;

  • 1st Jan to 31st Jan ---> 30days ---> will result in 0 (logical since it is not a full month)
  • 1st Feb to 1st Mar ---> 28 or 29 days ---> will result in 1 (logical since it is a full month)
  • 15th Feb to 15th Mar ---> 28 or 29 days ---> will result in 1 (logical since a month passed)
  • 31st Jan to 1st Feb ---> 1 day ---> will result in 0 (obvious but the mentioned answer in the post results in 1 month)
心的位置 2024-09-02 18:19:07

JavaScript 中两个日期之间的月份差异:

 start_date = new Date(year, month, day); //Create start date object by passing appropiate argument
 end_date = new Date(new Date(year, month, day)

start_date 和 end_date 之间的总月份:

 total_months = (end_date.getFullYear() - start_date.getFullYear())*12 + (end_date.getMonth() - start_date.getMonth())

Difference in Months between two dates in JavaScript:

 start_date = new Date(year, month, day); //Create start date object by passing appropiate argument
 end_date = new Date(new Date(year, month, day)

total months between start_date and end_date :

 total_months = (end_date.getFullYear() - start_date.getFullYear())*12 + (end_date.getMonth() - start_date.getMonth())
未蓝澄海的烟 2024-09-02 18:19:07

您还可以考虑此解决方案,此函数以整数或数字形式返回月份差异

开始日期作为第一个或最后一个param,是容错的。这意味着该函数仍将返回相同的值。

const diffInMonths = (end, start) => {
   var timeDiff = Math.abs(end.getTime() - start.getTime());
   return Math.round(timeDiff / (2e3 * 3600 * 365.25));
}

const result = diffInMonths(new Date(2015, 3, 28), new Date(2010, 1, 25));

// shows month difference as integer/number
console.log(result);

You could also consider this solution, this function returns the month difference in integer or number

Passing the start date as the first or last param, is fault tolerant. Meaning, the function would still return the same value.

const diffInMonths = (end, start) => {
   var timeDiff = Math.abs(end.getTime() - start.getTime());
   return Math.round(timeDiff / (2e3 * 3600 * 365.25));
}

const result = diffInMonths(new Date(2015, 3, 28), new Date(2010, 1, 25));

// shows month difference as integer/number
console.log(result);

喜爱皱眉﹌ 2024-09-02 18:19:07

我知道这真的很晚了,但无论如何还是发布它以防对其他人有帮助。这是我想出的一个函数,它似乎可以很好地计算两个日期之间的月份差异。诚然,它比 Mr.Crowder 的更加粗俗,但通过单步执行日期对象提供了更准确的结果。它是在 AS3 中,但您应该能够放弃强类型,并且您将拥有 JS。请随意让外面的人看起来更漂亮!

    function countMonths ( startDate:Date, endDate:Date ):int
    {
        var stepDate:Date = new Date;
        stepDate.time = startDate.time;
        var monthCount:int;

        while( stepDate.time <= endDate.time ) { 
            stepDate.month += 1;
            monthCount += 1;
        }           

        if ( stepDate != endDate ) { 
            monthCount -= 1;
        }

        return monthCount;
    }

I know this is really late, but posting it anyway just in case it helps others. Here is a function I came up with that seems to do a good job of counting differences in months between two dates. It is admittedly a great deal raunchier than Mr.Crowder's, but provides more accurate results by stepping through the date object. It is in AS3 but you should just be able to drop the strong typing and you'll have JS. Feel free to make it nicer looking anyone out there!

    function countMonths ( startDate:Date, endDate:Date ):int
    {
        var stepDate:Date = new Date;
        stepDate.time = startDate.time;
        var monthCount:int;

        while( stepDate.time <= endDate.time ) { 
            stepDate.month += 1;
            monthCount += 1;
        }           

        if ( stepDate != endDate ) { 
            monthCount -= 1;
        }

        return monthCount;
    }
熊抱啵儿 2024-09-02 18:19:07

为了扩展@TJ的答案,如果您正在寻找简单的月份,而不是完整的日历月份,您可以只检查 d2 的日期是否大于或等于 d1 的日期。也就是说,如果 d2 的月份晚于 d1 的月份,则多了 1 个月。所以你应该能够这样做:

function monthDiff(d1, d2) {
    var months;
    months = (d2.getFullYear() - d1.getFullYear()) * 12;
    months -= d1.getMonth() + 1;
    months += d2.getMonth();
    // edit: increment months if d2 comes later in its month than d1 in its month
    if (d2.getDate() >= d1.getDate())
        months++
    // end edit
    return months <= 0 ? 0 : months;
}

monthDiff(
    new Date(2008, 10, 4), // November 4th, 2008
    new Date(2010, 2, 12)  // March 12th, 2010
);
// Result: 16; 4 Nov – 4 Dec '08, 4 Dec '08 – 4 Dec '09, 4 Dec '09 – 4 March '10

这并不能完全解释时间问题(例如 3 月 3 日下午 4:00 和 4 月 3 日下午 3:00),但它更准确,并且只需几行代码。

To expand on @T.J.'s answer, if you're looking for simple months, rather than full calendar months, you could just check if d2's date is greater than or equal to than d1's. That is, if d2 is later in its month than d1 is in its month, then there is 1 more month. So you should be able to just do this:

function monthDiff(d1, d2) {
    var months;
    months = (d2.getFullYear() - d1.getFullYear()) * 12;
    months -= d1.getMonth() + 1;
    months += d2.getMonth();
    // edit: increment months if d2 comes later in its month than d1 in its month
    if (d2.getDate() >= d1.getDate())
        months++
    // end edit
    return months <= 0 ? 0 : months;
}

monthDiff(
    new Date(2008, 10, 4), // November 4th, 2008
    new Date(2010, 2, 12)  // March 12th, 2010
);
// Result: 16; 4 Nov – 4 Dec '08, 4 Dec '08 – 4 Dec '09, 4 Dec '09 – 4 March '10

This doesn't totally account for time issues (e.g. 3 March at 4:00pm and 3 April at 3:00pm), but it's more accurate and for just a couple lines of code.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文