在 JavaScript 中获取 2 个日期之间的差异?

IT技术 javascript date
2021-01-31 19:25:25

我如何在全天中获得 2 个日期之间的差异(我不想要一天的任何部分)

var date1 = new Date('7/11/2010');
var date2 = new Date('12/12/2010');
var diffDays = date2.getDate() - date1.getDate(); 
alert(diffDays)

我尝试了上面的方法,但这没有用。

6个回答

这是一种方法

const date1 = new Date('7/13/2010');
const date2 = new Date('12/15/2010');
const diffTime = Math.abs(date2 - date1);
const diffDays = Math.ceil(diffTime / (1000 * 60 * 60 * 24)); 
console.log(diffTime + " milliseconds");
console.log(diffDays + " days");

请注意,我们需要将日期括在引号中。其余代码获取以毫秒为单位的时间差,然后除以获取天数。日期需要 mm/dd/yyyy 格式。

同样,使用您的方法可以获得 1 天,因为getDate()返回日期而不考虑月份。因此,您将得到 12 - 11 = 1。
2021-03-16 19:25:25
在计算的跨度中一天 23 小时 25 小时不工作。在设计这样的计算之前,咨询 UTC(世界协调时间)和“民用”时间标准的详细处理会很有帮助。一天并不总是 86,400 秒,即使在 UTC 中也不例外。但是,ECMA 标准声明它不会有 58、59、61 或 62 秒的分钟数,这种情况在 UTC 中每年最多出现两次。您不能假设其他语言和操作系统中与纪元(1970 年 1 月 1 日 00:00:00 时)的偏移量是相同的,因为其中一些具有 58、59、61 和 62 秒分钟。
2021-03-17 19:25:25
正如 volkan 在下面回答的那样,1000 * 3600 * 24 是每天的毫秒数。至于总是返回一个正数,这是一个特性:) 通常,当人们谈论两个日期之间的天数时,该数字是正数。如果方向很重要,只需删除 Math.abs()。
2021-03-23 19:25:25
为了在夏令时正常工作,Math.round 应该替换 Math.ceil。但我认为 Shyam 的答案是要走的路。
2021-04-04 19:25:25
日期已经返回的时间不需要调用 .getTime()
2021-04-07 19:25:25

更正确的解决方案

...因为日期自然具有时区信息,可以跨越具有不同夏令时调整的区域

此问题的先前答案未考虑所讨论的两个日期跨越夏令时 (DST) 更改的情况。DST 更改发生的日期将以毫秒为单位的持续时间为!= 1000*60*60*24,因此典型计算将失败。

您可以通过首先将两个日期标准化为 UTC,然后计算这两个 UTC 日期之间的差异来解决此问题。

现在,解决方案可以写成,

const _MS_PER_DAY = 1000 * 60 * 60 * 24;

// a and b are javascript Date objects
function dateDiffInDays(a, b) {
  // Discard the time and time-zone information.
  const utc1 = Date.UTC(a.getFullYear(), a.getMonth(), a.getDate());
  const utc2 = Date.UTC(b.getFullYear(), b.getMonth(), b.getDate());

  return Math.floor((utc2 - utc1) / _MS_PER_DAY);
}

// test it
const a = new Date("2017-01-01"),
    b = new Date("2017-07-25"),
    difference = dateDiffInDays(a, b);

这是有效的,因为 UTC 时间从不观察 DST。请参阅UTC 是否遵守夏令时?

ps 在讨论了有关此答案的一些评论之后,一旦您了解了跨越 DST 边界的 javascript 日期问题,解决它的方法可能不止一种。我上面提供的是一个简单(并经过测试)的解决方案。我很想知道是否有一个简单的基于算术/数学的解决方案,而不必实例化两个新的 Date 对象。这可能会更快。

可能是因为@chobo2 还没回来看这个问题
2021-03-10 19:25:25
@Ai_boy:虽然这是逻辑上最正确的答案,但没有任何值无法匹配更简单的Math.round((b - a)/ _MS_PER_DAY, 0),因此很难支持“唯一正确的答案”。
2021-03-11 19:25:25
@ShyamHabarakada:这是 aMath.ceilMath.floor技术的问题,但由于夏令时仅从一天 24 小时调整一小时,它将被Math.round. 我还没有进行详尽的测试,但我看不出两者有什么不同。你是否可以?我们实际上是在18347050 中讨论这个问题的,这就是我遇到这个旧线程的方式,我那里提到了夏令时。
2021-03-24 19:25:25
这是唯一正确的答案,我不明白为什么接受其他答案
2021-04-03 19:25:25
使用 UTC 而不是本地时区将更正民用时间系统中由 23 小时制和 25 小时制引起的问题。UTC 也有 58、59、61 和 62 秒分钟,最多一年两次,因此 UTC 中的一天并不总是有 86,400 秒。但是,ECMA 标准声明 JavaScript 没有包含这些调整,因此在纯 JavaScript 中工作时忽略它们。但是,其他系统不会忽略它们,并且您不能假设从纪元时刻(1970 年 1 月 1 日 00:00:00)开始的偏移量在编程语言和操作系统之间总是相同的。
2021-04-08 19:25:25

这是使用moment.js的解决方案

var a = moment('7/11/2010','M/D/YYYY');
var b = moment('12/12/2010','M/D/YYYY');
var diffDays = b.diff(a, 'days');
alert(diffDays);

我使用了您的原始输入值,但您没有指定格式,因此我假设第一个值是 7 月 11 日。如果原定于 11 月 7 日,则将格式调整为D/M/YYYY

请注意,moment.js 是一个很大的依赖项
2021-03-15 19:25:25
干杯,我正在寻找一个 momentjs 解决方案
2021-03-19 19:25:25
2021-03-22 19:25:25
@Matt Johnson:我需要找到确切的差异,我的意思是,从这个时间到未来日期的剩余天数、小时数、分钟数和秒数?怎么做?
2021-03-23 19:25:25
var date1 = new Date("7/11/2010");
var date2 = new Date("8/11/2010");
var diffDays = parseInt((date2 - date1) / (1000 * 60 * 60 * 24), 10); 

alert(diffDays )
date2 - date1 => 毫秒输出 (1000 * 60 * 60 * 24) => 毫秒到天
2021-03-09 19:25:25
克里斯蒂安:他想要一个整数。parseInt 可能是最糟糕的方法。Math.round 是“正常”的方式;它舍入而不是截断。如果需要截断,将表达式与 0 '或'就足够了:(date2 - date1) / (1000 * 60 * 60 * 24) | 0
2021-03-19 19:25:25
@ontananzavar date1 = new Date("2015-04-04"); var date2 = new Date("2015-04-06"); parseInt((date2 - date1) / (1000 * 60 * 60 * 24));为我产生 2
2021-04-01 19:25:25
请注意,此解决方案并不完全准确,因为在某些情况下,即 2015-04-06 减去 2015-04-04 给出了错误的 1 天,所有关于 parseInt() 方法。
2021-04-03 19:25:25
parseInt 是不是完全没有必要?
2021-04-04 19:25:25

我尝试了很多方法,发现使用datepicker 是最好的,但是日期格式会导致JavaScript 出现问题....

所以这是我的答案,可以开箱即用。

<input type="text" id="startdate">
<input type="text" id="enddate">
<input type="text" id="days">

<script src="https://code.jquery.com/jquery-1.8.3.js"></script>
<script src="https://code.jquery.com/ui/1.10.0/jquery-ui.js"></script>
<link rel="stylesheet" href="http://code.jquery.com/ui/1.10.3/themes/redmond/jquery-ui.css" />
<script>
$(document).ready(function() {

$( "#startdate,#enddate" ).datepicker({
changeMonth: true,
changeYear: true,
firstDay: 1,
dateFormat: 'dd/mm/yy',
})

$( "#startdate" ).datepicker({ dateFormat: 'dd-mm-yy' });
$( "#enddate" ).datepicker({ dateFormat: 'dd-mm-yy' });

$('#enddate').change(function() {
var start = $('#startdate').datepicker('getDate');
var end   = $('#enddate').datepicker('getDate');

if (start<end) {
var days   = (end - start)/1000/60/60/24;
$('#days').val(days);
}
else {
alert ("You cant come back before you have been!");
$('#startdate').val("");
$('#enddate').val("");
$('#days').val("");
}
}); //end change function
}); //end ready
</script>

一个小提琴可以在这里看到演示

这与我在此解决方案中遇到的问题类似,如果用户首先单击 date2 日期选择器,则它会失败。
2021-03-11 19:25:25