当前位置: 首页 > 知识库问答 >
问题:

是否将日期、时间和UTC偏移量值转换为自unix纪元以来的毫秒?

邹驰
2023-03-14

我正在从事一个机器人项目,该项目有来自不同位置的传感器数据,精度为毫秒(gps同步ntp在1ms内)。

如何将历史日期、时间和UTC偏移量组件转换为自unix纪元以来的毫秒?也就是说,全部YYYY-mm-dd HH:mm:SS。mS/-UTC offset作为单个整数而不是字符串提供。

偏移量考虑到夏令时,例如UTC 1的时区在夏令时的UTC偏移量为2。

有一个类似的帖子,但是它以字符串格式处理日期时间,没有UTC偏移信息。

该帖子的公认答案是使用mktime,但在这篇文章中,一位60K代表用户评论说:

mktime将使用计算机的区域设置将该日期/时间转换为GMT。如果不想减去本地时区,请使用mkgmtime。

我已经确认mktime确实执行时区转换,这取决于夏令时标志tm_isdst。我没有信息是否在夏令时进行观测,只有它们与UTC的偏移量。

从unix纪元开始,用UTC偏移量将历史日期时间转换为毫秒的可靠方法是什么?

共有3个答案

甄阳朔
2023-03-14

如果您有UTC小时 /-时区,您可以首先使用mktime(如链接的答案所述)将日期/时间转换为自纪元以来的秒。然后,添加/减去时区差异。

编辑:

由于mktime函数假定给定的时间是当前时区的时间,因此还需要将结果移动该值。

首先,运行tzset()函数。这将设置两个全局变量timezone,它是当前时间落后于GMT的秒数;以及daylight,它指示夏令时是否生效。

struct tm my_time;
// populate fields
int my_tz;
// set to timezone in question as seconds ahead of UTC
time_t t = mktime(&my_time);
t += timezone;
if (daylight) {
    t -= 3600;
}
t -= my_tz;
袁志专
2023-03-14

如果你看看你提到的问题的公认答案,它涉及单个整数。它将字符串拆分为部分,将其转换为整数,然后使用它们。放下转换部分。

tm t;
// Fill tm_sec, tm_min, tm_hour and so on
return (mktime(&t) - tz * SECONDS_IN_TIMEZONE) * 1000 + milliseconds

如果时区是整数,可以将其乘以时区中的秒数,然后从时间中减去If。4区域表示时间比UTC大4小时。还要注意的是,并非所有时区都有完整的小时数。因此,您可能希望以秒/毫秒或至少分钟为单位存储时区。

璩华辉
2023-03-14

这是一个免费的、开源的C 11/14头文件库,可以完成这项工作。它有完整的文档记录,可移植到所有C 11/14实现中。甚至还有一个视频演示。

#include "chrono_io.h"
#include "date.h"
#include <iostream>
#include <sstream>

int
main()
{
    using namespace std;
    using namespace std::chrono;
    using namespace date;
    istringstream in{"2016-10-10 23:48:59.456 -4"};
    sys_time<milliseconds> tp;
    int ih;
    in >> parse("%F %T", tp) >> ih;
    tp -= hours{ih};
    cout << tp.time_since_epoch() << '\n';
}

这将产生:

1476157739456ms

这是自纪元以来正确的Unix时间毫秒数。如果需要包含闰秒,在上面的链接中有相应的功能,但这部分不仅仅是标题(需要使用IANA时区数据库)。

这个库是

如果您的输入流遵循标准UTC偏移量语法/-hhmm而不是/-[h]h,则代码可以简化为:

istringstream in{"2016-10-10 23:48:59.456 -0400"};
sys_time<milliseconds> tp;
in >> parse("%F %T %z", tp);

这将为tp输出完全相同的值。

1476157739456ms

还支持这种修改后的语法:

istringstream in{"2016-10-10 23:48:59.456 -4:00"};
sys_time<milliseconds> tp;
in >> parse("%F %T %Ez", tp);

如果您想要毫秒的整数值,这在中可用

cout << tp.time_since_epoch().count() << '\n';

1476157739456

不管你用什么方式来划分,这都是几行类型安全代码,没有显式的转换因子。

我注意到你用[c]和[c]标记了你的问题。这个答案只针对C语言。C和C是两种不同的语言,如果你必须用C编程,那么在C抽象级别编程的其他答案之一会更好。

出于好奇,如果您只输出tp

cout << tp << '\n';

然后它输出预期的UTC时间戳:

2016-10-11 03:48:59.456

 类似资料:
  • 上下文是,我们的产品中有一个现有的应用程序,它生成并向现有的oracle过程发送纪元号&反之亦然。它在该过程中使用如下内容 当我尝试这些查询时,它对我也适用于Oracle10g服务器(如果有关系的话,还有Oracle sql Developer4.x)。 在现有的过程中,要求将值保存为日期本身(时间组件与日期无关),但是在新的要求中,我必须将unix EPOCH值转换为日期时间(小时/分钟/秒级别

  • 问题内容: 为您准备的头抓板。 我正在从IPInfoDB的API中获取地理IP数据,它从UTC返回 包括 DST 的时区偏移(如果当前已反映)。 例如,我住在EST(-5),目前是DST,因此geo IP API返回()作为偏移量。 因为DST令人头疼,所以这太好了。但是令我惊讶的是,它又引起了头疼。 我将此数据加载到PHP中,以通过AJAX传递给应用程序。我想在应用程序上获取IP地址的实时本地时

  • 问题内容: 我已经为此战斗了一段时间。我正在尝试将纪元转换为日期对象。时代以UTC发送给我。每当您经过一个纪元时,它就会假定它是本地纪元。我尝试创建一个UTC对象,然后使用它来将其调整为适当的纪元,但是似乎有用的唯一方法是字符串对我没有帮助。如果我将该字符串传递给新日期,则应该注意它是UTC,但不是。 我的下一个尝试是尝试获取本地当前时间段与UTC当前时间段之间的差异,但是我也无法做到这一点。 它

  • 问题内容: 我对当前UTC时间以毫秒为单位不感兴趣,也无需弄乱时区。我的原始日期已经存储为UTC时间戳。 我在UTC时间“ 2012-06-14 05:01:25”中存储了一个日期。我对日期时间不感兴趣,但对日期部分感兴趣。因此,在用Java检索日期并排除小时,分钟和秒之后,我剩下的是“ 2012-06-14”。 如何将其转换为UTC毫秒? 问题答案: 编辑:我错过了“忽略一天中的时间”部分。它现

  • 问题内容: 我有一个Python 对象,我想将其转换为Unix时间,即自1970年以来的秒/毫秒。 我该怎么做呢? 问题答案: 在我看来,最简单的方法是