我想在JavaScript中解析一个没有时区的日期。我试着:

new Date(Date.parse("2005-07-08T00:00:00+0000"));

返回2005年7月8日星期五02:00:00 GMT+0200(中欧夏令时):

new Date(Date.parse("2005-07-08 00:00:00 GMT+0000"));

返回相同的结果,并且:

new Date(Date.parse("2005-07-08 00:00:00 GMT-0000"));

也返回相同的结果。

我想解析时间:

没有时区。 而不调用构造函数Date。UTC或new日期(年、月、日)。 通过简单地将一个字符串传递到Date构造函数(没有原型方法)。

我必须生成一个Date对象,而不是String对象。


当前回答

JavaScript中的日期只是在内部保持简单,因此日期-时间数据以UTC Unix历元(毫秒或毫秒)存储。

如果你想有一个“固定”的时间,无论你在地球上的任何时区都不会改变,你可以调整UTC时间以匹配当前的本地时区并保存它。在检索它时,无论您所在的本地时区是什么,它都会根据保存它的时区显示调整后的UTC时间,然后添加本地时区偏移量以获得“固定”时间。

保存日期(毫秒):

toUTC(datetime) {
  const myDate = (typeof datetime === 'number')
    ? new Date(datetime)
    : datetime;

  if (!myDate || (typeof myDate.getTime !== 'function')) {
    return 0;
  }

  const getUTC = myDate.getTime();
  const offset = myDate.getTimezoneOffset() * 60000; // It's in minutes so convert to ms
  return getUTC - offset; // UTC - OFFSET
}

检索/显示日期(毫秒):

fromUTC(datetime) {
  const myDate = (typeof datetime === 'number')
    ? new Date(datetime)
    : datetime;

  if (!myDate || (typeof myDate.getTime !== 'function')) {
    return 0;
  }

  const getUTC = myDate.getTime();
  const offset = myDate.getTimezoneOffset() * 60000; // It's in minutes so convert to ms
  return getUTC + offset; // UTC + OFFSET
}

然后你可以:

const saveTime = new Date(toUTC(Date.parse("2005-07-08T00:00:00+0000")));
// SEND TO DB....

// FROM DB...
const showTime = new Date(fromUTC(saveTime));

其他回答

我遇到了同样的问题,然后想起了我正在从事的一个遗留项目的一些问题,以及他们是如何处理这个问题的。当时我并不理解,也并不在意,直到我自己遇到了这个问题

var date = '2014-01-02T00:00:00.000Z'
date = date.substring(0,10).split('-')
date = date[1] + '-' + date[2] + '-' + date[0]

new Date(date) #Thu Jan 02 2014 00:00:00 GMT-0600

不管出于什么原因,将日期传递为“01-02-2014”将时区设置为0并忽略用户的时区。这可能是Date类中的一个侥幸,但它在一段时间以前就存在,今天也存在。而且它似乎可以跨浏览器工作。你自己试试吧。

这段代码是在一个全局项目中实现的,在这个项目中,时区很重要,但查看日期的人并不关心它被引入的确切时间。

日期被正确解析,只是toString将其转换为您的本地时区:

let s = "2005-07-08T11:22:33+0000"; let d = new Date(Date.parse(s)); //此日志为我 //“2005年7月8日星期五13:22:33 GMT+0200(中欧夏季时间)” //和其他东西给你 console.log (d.toString ()) //此日志 //星期五,2005年7月8日11:22:33 GMT // for everyone console.log (d.toUTCString ())

Javascript Date对象是时间戳-它们只包含从epoch开始的毫秒数。Date对象中没有时区信息。这个时间戳代表哪个日历日期(日、分、秒)是一个解释问题(其中一个是…字符串方法)。

上面的例子显示日期被正确地解析了——也就是说,它实际上包含了一个毫秒数,对应于GMT的"2005-07-08T11:22:33"。

我个人更喜欢@wawka的答案,然而,我也提出了一个不那么干净的技巧来解决这个问题,这是更简单的,如果你确定你想转换的字符串的格式,可以工作。

请看下面的代码片段:

var dateString = 2021- 08-02t00 var dateObj =新日期(数据+ z) 日志控制台。 var dateObjWithTZ =新日期 log控制台(“正常转换:”,dateObjWithTZ)

这在这种情况下是有效的,因为在日期时间字符串的末尾添加Z将使JS将此字符串视为UTC日期字符串,因此它不会向其添加时区差异。

因为它确实是一个格式问题时显示日期(例如显示在本地时间),我喜欢使用新的(ish) Intl。DateTimeFormat对象来执行格式化,因为它更显式,并提供更多输出选项:

const dateOptions = { timeZone: 'UTC', month: 'long', day: 'numeric', year: 'numeric' };

const dateFormatter = new Intl.DateTimeFormat('en-US', dateOptions);
const dateAsFormattedString = dateFormatter.format(new Date('2019-06-01T00:00:00.000+00:00'));

console.log(dateAsFormattedString) // "June 1, 2019"

如所示,通过将timeZone设置为“UTC”,它将不会执行本地转换。作为奖励,它还允许您创建更精致的输出。你可以阅读更多关于国际。DateTimeFormat对象。

无需创建新的Intl就可以实现相同的功能。DateTimeFormat对象。简单地将语言环境和日期选项直接传递给toLocaleDateString()函数。

const dateOptions = { timeZone: 'UTC', month: 'long', day: 'numeric', year: 'numeric' };
const myDate = new Date('2019-06-01T00:00:00.000+00:00');
myDate.toLocaleDateString('en-US', dateOptions); // "June 1, 2019"

我发现JavaScript日期对象和时区|修复一个“关闭1天”的错误在YouTube上。这将修复/重置本地时区的偏移。视频中对这个问题有一个很好的解释。

//日期为YYYY-MM-DDT00:00:00Z let dateFormat =新的日期(日期) // Date对象上的方法将从UTC转换为用户时区 //设置分钟值为当前分钟(UTC) +用户本地时间(UTC)偏移量 dateFormat.setMinutes(dateFormat.getMinutes() + dateFormat.getTimezoneOffset()) //现在我们可以在日期obj上使用方法而不进行时区转换 let dateStr = dateFormat.toDateString();