Ответ 1
Если вы беспокоитесь о повторной установке в localtime
и gmtime
, есть localtime_r
и gmtime_r
, которые могут обрабатывать несколько вызовов.
Когда вам нужно форматировать время по своему усмотрению, проверьте функцию strftime
.
Я ищу способ сохранить время в моделях HH:: MM:: SS на С++. Я видел здесь, что у них много решений, и после небольшого исследования я выбрал time
и localtime
. Однако, кажется, что функция localtime
немного сложна, так как она говорит:
Все вызовы localtime и gmtime используют одну и ту же статическую структуру, поэтому каждый вызов перезаписывает результаты предыдущего вызова.
Проблема, вызвавшая это, показана в следующем фрагменте кода:
#include <ctime>
#include <iostream>
using namespace std;
int main() {
time_t t1 = time(0); // get time now
struct tm * now = localtime( & t1 );
std::cout << t1 << std::endl;
sleep(2);
time_t t2 = time(0); // get time now
struct tm * now2 = localtime( & t2 );
std::cout << t2 << std::endl;
cout << (now->tm_year + 1900) << '-'
<< (now->tm_mon + 1) << '-'
<< now->tm_mday << ", "
<< now->tm_hour << ":" << now->tm_min << ":" << now->tm_sec
<< endl;
cout << (now2->tm_year + 1900) << '-'
<< (now2->tm_mon + 1) << '-'
<< now2->tm_mday << ", "
<< now2->tm_hour << ":" << now2->tm_min << ":" << now2->tm_sec
<< endl;
}
Типичный выход для этого:
1320655946
1320655948
2011-11-7, 9:52:28
2011-11-7, 9:52:28
Итак, как вы можете видеть, отметки времени time_t
верны, но местное время все испортит.
Мой вопрос: как преобразовать временную метку с типом time_t
в человеко-читаемое время?
Если вы беспокоитесь о повторной установке в localtime
и gmtime
, есть localtime_r
и gmtime_r
, которые могут обрабатывать несколько вызовов.
Когда вам нужно форматировать время по своему усмотрению, проверьте функцию strftime
.
вызов localtime() сохраняет результаты во внутреннем буфере.
Каждый раз, когда вы его вызываете, вы перезаписываете буфер.
Альтернативным решением было бы сделать копию буфера.
time_t t1 = time(0); // get time now
struct tm* now = localtime( & t1 ); // convert to local time
struct tm copy = *now; // make a local copy.
// ^^^ notice no star.
Но обратите внимание: единственный раз, когда вы должны преобразовывать в локальное время, вы указываете значение. В любое другое время вы должны просто сохранить время как UTC (для хранения и манипуляции). Поскольку вы только конвертируете объекты для преобразования отображения, затем печатайте сразу, а затем все будет не так.
localtime
имеет то, что лучше всего считать устаревшим интерфейсом. Это не может быть
например, в многопоточном коде. В многопоточном
среды, вы можете использовать localtime_r
под Posix или localtime_s
под Windows. В противном случае все, что вам нужно сделать, это сохранить результаты:
tm then = *localtime( &t1 );
// ...
tm now = *localtime( &t2 );
Было бы, вероятно, более идиоматично, однако, только называть localtime
непосредственно перед форматированием вывода, например:
std::string
timestampToString( time_t timeAndDate )
{
char results[100];
if ( strftime( results, sizeof( results ), "%Y-%m-%d, %H:%M:%S",
localtime( &timeAndDate) ) == 0 ) {
assert( 0 );
}
return results;
}
а затем запись:
std::cout << formatTime( t1 ) << std::endl;
(Вы также можете создать более общую функцию форматирования, которая формат в качестве аргумента.)
Вы можете запускать непрерывные часы, используя следующий код. Он работает красиво.
#include<iostream>
#include <Windows.h>
#include<ctime>
using namespace std;
void main() {
while(true) {
system("cls"); //to clear screen
time_t tim;
time(&tim);
cout << ctime(&tim);
Sleep(1);
}
}