如何在c ++ 11中操作日期/日期时间?

时间:2013-04-05 18:26:08

标签: c++ c++11

这很令人尴尬,但我很难对日期时间进行简单的操作。

这是我基本上尝试使用c ++ 11实现的c#版本;

DateTime date1=new DateTime(4,5,2012);
DateTime date2=new DateTIme(7,8,2013);
int day1=date1.Days;
TimeSpan ts=d2-d1;
int diffDays=ts.Days;

我尝试了什么?

    std::tm tm;
    tm.tm_year=113;
    tm.tm_mon=0;
    tm.tm_wday=0;

    std::time_t tt=mktime(&tm);
    std::chrono::system_clock::time_point then = std::chrono::system_clock::from_time_t(tt);
    std::chrono::system_clock::time_point now = std::chrono::system_clock::now();
    auto e1 = std::chrono::duration_cast<std::chrono::hours>(now - then).count();

e1(379218)的价值毫无意义。

我看了一下chrono,它是作为日期时间的c ++ 11标准库提供的,但我找不到如何创建int year = 2012,int month = 2,int day的日期的示例= 14

PS:chrono是否足以处理c ++ 11中的日期/时间/时区?是否需要time.h?

2 个答案:

答案 0 :(得分:7)

旧问题的新答案。

除了讨论古老的std::tm之外,C ++ 11没有办法处理日期或日期时间,boost Date Time除外。还有一个我最近一直在研究的库,它非常倾向于性能,编译时类型安全性和chrono兼容性。如上所述它只适用于C ++ 14,但如果你退出一些constexpr,它将适用于C ++ 11。它只是标题,只包含一个标题,并记录在案here它的I / O能力很强。(现在具有广泛的I / O功能)

但这是你的例子的样子:

哦,现在我仔细观察,不知道C#,我不知道DateTime(4,5,2012)是指2012年4月5日还是2012年5月4日.m / d / y和d / m / y格式被广泛使用。这是我的图书馆解决的问题之一。它明确地接受这两种格式。对于这个演示,我将假设您正在以m / d / y格式编写。但我将使用这两种格式来重现您的示例:

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

int
main()
{
//     DateTime date1=new DateTime(4,5,2012);
//     DateTime date2=new DateTIme(7,8,2013);
//     int day1=date1.Days;
//     TimeSpan ts=d2-d1;
//     int diffDays=ts.Days;

    using namespace date;
    auto date1 = sys_days(apr/5/2012);     // m/d/y is ok
    auto date2 = sys_days(8_d/jul/2013);   // d/m/y is ok
                                           // y/m/d is also ok
    auto diffDays = date2 - date1;         // diffDays is a chrono::duration
    std::cout << diffDays.count() << '\n';
}

这将输出:

459

在C ++ 14中,这个计算实际上可以在编译时完成:

constexpr auto date1 = sys_days(apr/5/2012);
constexpr auto date2 = sys_days(8_d/jul/2013);
constexpr auto diffDays = date2 - date1;
static_assert(diffDays == days{459}, "");

这意味着“日期常量”既可读也非常有效,可编译为“立即加载”。

有关完整说明,教程和实施的信息,请参阅the documentation

答案 1 :(得分:5)

您需要初始化tm中的所有字段,以

开头
std::tm tm = {0,0,0,0,0,0,0,0,0,0,0};

如果没有这个,其他字段(之后未明确设置的字段)将包含任意值。转换也会对值进行标准化,这意味着如果字段tm_hour包含123456789,则会在您指定的日期添加这么多小时。这就是解释e1的无意义值的方法。如果您显式初始化所有字段,它将允许您的示例返回有意义的值,但您可能需要设置更多字段,例如isdst,以使其适用于所有情况。

我必须承认,到目前为止我还没有使用chrono,因为我发现所需的语法过于冗长,并且我继续使用自己的类来包装C风格的时间函数。当然,这不是关于<chrono>的质量和力量的陈述,也许我应该开始使用它:)