2
\$\begingroup\$
  std::string time_string;
  if ( time_t_var > 0 ) {
      time_string = boost::posix_time::to_iso_extended_string(boost::posix_time::from_time_t(time_t_var));
      boost::replace_all(time_string , "T" , " ");
  }

I have the above to get a time_t to a string in the format Y:M:D H:M:S or simply a blank string in the instances where time_t is 00:00 hours, Jan 1, 1970 UTC.

The code above is in a function called once a second so I'm looking to get this done as fast as possible, boost's way seems to need another function call to replace the 'T' and it's a std::string so I'm needing to convert it to std::wstring after.

Is there a quicker method of doing this preferably by using a std::wstring to begin with?

\$\endgroup\$
  • 3
    \$\begingroup\$ You could use std::put_time. \$\endgroup\$ – Edward Dec 22 '16 at 0:44
  • \$\begingroup\$ Or you could use std::time_put and imbue the stream with it so that dates are always correctly formatted. \$\endgroup\$ – Martin York Dec 22 '16 at 18:02
4
\$\begingroup\$

Here's how to do this with std::put_time as mentioned in a comment.

#include <iostream>
#include <iomanip>
#include <ctime>
#include <sstream>

std::wstring wtime(const time_t &t) {
    std::tm tm = *std::localtime(&t);
    std::wstringstream wss;
    wss << std::put_time(&tm, L"%F %T");
    return wss.str();
}

int main()
{
    std::time_t t = std::time(nullptr);
    std::wstring timestr = wtime(t);
    std::wcout << timestr;
}

Sample output:

2016-12-22 12:33:28

Note that unlike Boost, there is no fractional second, so if you need that, you are probably better off keeping Boost. If that's the case, you can replace the unwanted T with this:

time_string[10] = ' ';

Since we know that the T character always is in the same place.

If this is really done once a second, it may be worthwhile to use a method that's often employed in embedded systems that need a text version of a clock: update a shared, read-only text version of the clock directly upon each tick.

\$\endgroup\$
  • \$\begingroup\$ Note to anybody who needs a std::string here instead of the wstring, you can modify the method given to use a std::stringstream, and remove the L from the second argument to put_time. \$\endgroup\$ – Alex K Dec 29 '18 at 10:29
1
\$\begingroup\$

I'm wondering if the ctime functions would work for you. This function will accept a time_t object and return the formatted wstring:

wstring GetTime(time_t& time_t_var)
{
    if ( time_t_var > 0 )
    {
        wchar_t buffer[30];
        wcsftime( buffer , 30 , L"%y:%m:%d %X" , localtime( &time_t_var ) );
        return buffer;
    }
    return L"";
}
\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.