C++ C++;11以字符串形式获取当前日期和时间

C++ C++;11以字符串形式获取当前日期和时间,c++,datetime,c++11,C++,Datetime,C++11,在c++11中,以字符串形式获取日期和时间的最新方法是什么 我知道std::put_time,但参考资料说我只能在流中使用它 有std::chrono::system\u clock提供到时间的返回时间为time\t,并且没有日期,不是吗 我可以使用像bames53这样的stringstream:但这似乎是一个解决办法 您可以使用下面给出的代码片段,因为它可以满足您的需要。这里为所需的localtime()函数使用time.h头文件,然后使用带有所需参数的strftime()函数将给出输出,并将

在c++11中,以字符串形式获取日期和时间的最新方法是什么

我知道std::put_time,但参考资料说我只能在流中使用它

std::chrono::system\u clock
提供
到时间的
返回时间为
time\t
,并且没有日期,不是吗


我可以使用像bames53这样的stringstream:但这似乎是一个解决办法

您可以使用下面给出的代码片段,因为它可以满足您的需要。这里为所需的localtime()函数使用time.h头文件,然后使用带有所需参数的strftime()函数将给出输出,并将其作为字符串返回

#include <iostream>
#include <string>
#include <time.h>
std::string current_date();
std::string current_time();
int main(){
    std::cout<<"Current date => "<<current_date()<<"\n";
    std::cout<<"Current time => "<<current_time()<<"\n";
}
std::string current_date(){
    time_t now = time(NULL);
    struct tm tstruct;
    char buf[40];
    tstruct = *localtime(&now);
    //format: day DD-MM-YYYY
    strftime(buf, sizeof(buf), "%A %d/%m/%Y", &tstruct);
    return buf;
}
std::string current_time(){
    time_t now = time(NULL);
    struct tm tstruct;
    char buf[40];
    tstruct = *localtime(&now);
    //format: HH:mm:ss
    strftime(buf, sizeof(buf), "%X", &tstruct);
    return buf;
}
#包括
#包括
#包括
std::字符串当前_日期();
std::字符串current_time();
int main(){

std::cout首先,
std::time\u t
确实捕获了日期和时间,因为它通常表示从1970年1月1日开始的秒数

在C++11中没有很好的处理日期的支持。如果您不想手动处理日期,您仍然必须依赖boost。下面是如何手动处理日期

您可以以线程安全的方式将其与任何
std::chrono::*clock
一起使用,例如
std::system\u clock
,如下所示:

std::string get_date_string(std::chrono::time_point t) {
  auto as_time_t = std::chrono::system_clock::to_time_t(t);
  struct tm tm;
  if (::gmtime_r(&as_time_t, &tm))
    if (std::strftime(some_buffer, sizeof(some_buffer), "%F", &tm))
      return std::string{some_buffer};
  throw std::runtime_error("Failed to get current date as string");
}
在其他地方,您可以发布:

get_date_string(std::system_clock::now());

这个解决方案的相对优点是,在API级别,您仍然使用现代的、可移植的C++概念,如:代码> STD::Time::TimeSyPosio,当然, STD::String

时间戳,像这样;

#include <iostream>
#include <chrono>
#include <ctime>

int main() {

    std::chrono::time_point<std::chrono::system_clock> now = std::chrono::system_clock::now();
    std::time_t start_time = std::chrono::system_clock::to_time_t(now);
    char timedisplay[100];
    struct tm buf;
    errno_t err = localtime_s(&buf, &start_time);
    if (std::strftime(timedisplay, sizeof(timedisplay), "%H:%M:%S", &buf)) {
        std::cout << timedisplay << '\n';
    }
}
#包括
#包括
#包括
int main(){
std::chrono::time_point now=std::chrono::system_clock::now();
std::time\u t start\u time=std::chrono::system\u clock::to\u time\t(现在);
字符时间显示[100];
struct-tm-buf;
errno\u t err=localtime\u s(&buf,&start\u time);
if(std::strftime(timedisplay,sizeof(timedisplay),%H:%M:%S,&buf)){
标准::cout更简单:

string CurrentDate()
{
    std::time_t now = std::chrono::system_clock::to_time_t(std::chrono::system_clock::now());

    char buf[100] = {0};
    std::strftime(buf, sizeof(buf), "%Y-%m-%d", std::localtime(&now));
    return buf;
}
根据当时的情况调整格式

请注意,我怀疑这对多线程代码不起作用,因为
std::localtime()
返回指向内部结构的指针。

使用,可以在一行代码中以
std::string
的形式获取当前UTC时间:

std::string s = date::format("%F %T", std::chrono::system_clock::now());
我刚刚运行了这个,字符串包含:

2017-03-30 17:05:13.400455
没错,它甚至可以提供完整的精度。如果您不喜欢该格式,则所有的
strftime
格式标记都可用。如果您需要本地时间,还可以提供一个,尽管它不仅仅是标题

std::string s = date::format("%F %T %Z", date::make_zoned(date::current_zone(),
                                         std::chrono::system_clock::now()));
输出:

2017-03-30 13:05:13.400455 EDT

看。就我个人而言,我会远离std::chrono,但这是你的决定。在这方面,abhishek ratore的回答是非常好的。是的,date.h是100%线程安全的。它不使用底层线程不安全的C API,也不依赖于线程不安全的实践,例如设置环境变量。时区库也是线程安全的,包括首次使用时时区库的初始化(取决于C++11线程安全函数本地静态)。唯一依赖于用户提供的同步的部分是很少使用的功能,即在首次使用后重新加载时区数据库(应用程序运行数月后可能会使用该功能)。这一特点已被充分记录:感谢您提供了这个伟大的库Howard。我能够使用不安全且笨重的strftime()将7行替换为1行!请向标准委员会提出建议(如果您还没有)。谢谢@Ricky65!你可以在自述文件底部附近找到这个库的当前标准化过程:谢谢链接。希望它能变成C++20。太棒了!谢谢你的建议。很好。你可能想使用函数参数
std::chrono::system\u clock::time\u point
。缓冲区
一些缓冲区
是字符数组(例如,
char some_buffer[64];
),必须在函数内部声明,并且不能是静态的(否则整个线程的安全性将丢失)。您可以重用
std::string
内部缓冲区(调整大小,然后收缩)并且避免复制。因为返回了
std::string
,所以时态
std::string buf
是一个更好的选择。这将消除从字符缓冲区构造字符串的额外开销。在提供的示例中
return buf
=
std::string(buf)
,它调用
memcpy
将“buf”复制到新创建的返回sting中。毕竟:
std::string buf;buf.resize(40);…strftime((char*)buf.data(),40,“%A%d/%m/%Y”,&tstruct);