用JavaScript从期限计算最终到期日

用JavaScript从期限计算最终到期日,javascript,date,math,Javascript,Date,Math,我需要找到一种方法来使用JavaScript计算贷款的最终到期日,但需要考虑少于31或30天的月份 例如,如果我的期限为60个月(5年),我的开始日期为2015年1月31日,那么我的最终到期日将为2019年12月31日。现在,如果我的任期是62个月,我的最终到期日将是2020年2月28日。大多数JavaScript数学的问题是,我得到的结果是2020年3月3日,这是不正确的。有什么想法吗?这没有经过很好的测试,但它可能会满足你的需要。它涉及到重做Date API自动执行的一些计算,但它们并不太难

我需要找到一种方法来使用JavaScript计算贷款的最终到期日,但需要考虑少于31或30天的月份


例如,如果我的期限为60个月(5年),我的开始日期为2015年1月31日,那么我的最终到期日将为2019年12月31日。现在,如果我的任期是62个月,我的最终到期日将是2020年2月28日。大多数JavaScript数学的问题是,我得到的结果是2020年3月3日,这是不正确的。有什么想法吗?

这没有经过很好的测试,但它可能会满足你的需要。它涉及到重做Date API自动执行的一些计算,但它们并不太难:

var addMonths = (function() {
  var counts = {
    normal: [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31],
    leap:   [31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]
  };
  return function(startDate, months) {
    var endYear = startDate.getFullYear() + Math.ceil((months + startDate.getMonth()) / 12) - 1;
    var yearType = ((endYear % 4 == 0) && (endYear % 100 != 0)) || (endYear % 400 == 0) ? 'leap' : 'normal';
    var endMonth = (startDate.getMonth() + months) % 12;
    var endDate = Math.min(startDate.getDate(), counts[yearType][endMonth]);
    return new Date(endYear, endMonth, endDate);
  };
}());

var date = new Date(2015, 0, 31); // 2015-01-31
addMonths(date, 60); //=> 2020-01-31
addMonths(date, 61); //=> 2020-02-29
addMonths(date, 62); //=> 2020-03-31
addMonths(date, 63); //=> 2020-04-30
addMonths(date, 73); //=> 2021-02-28

请注意,我的数字似乎比你的少了一个月。我猜你是用第一次付款作为你的开始日期,而不是实际增加一个完整的补充,比如说,62个月。但是如果你愿意的话,这很容易调整一个。

加上你想要的年数和月数,然后找到该月的最后一天。添加Javascript日期将为您提供找到的结果,因此需要执行两个额外步骤:

function addMonths(month, year, term) {
    var endTerm = term - 1;     // adjust for zero index
    var newYear = year + parseInt(endTerm / 12); // add the years
    var newMonth = month + (endTerm % 12);  // add the remaining months
    if (newMonth > 12)  {     // remaining months into next year?
        newYear = newYear + 1;  
        newMonth = newMonth - 12;
    }
    var endDate = new Date(newYear, newMonth, 0); // get last day of month
    return endDate;
}
此解决方案符合您设置的参数。你需要检查角落的箱子。例如,期限为1个月表示当前月份的结束日期,期限为2个月表示下个月的结束日期

对于您的特定问题,这是一个非常简单的解决方案。如果你要做一组日期操作,那么考虑使用一个库。


这里有一个非常简单的问题:

当一个月的日期是29、30或31时,是否只有异常行为?是的,正如Scott所建议的,硬编码异常似乎是最快的方式。谢谢大家@ScottSauyet的建议奏效了!!