elapsed time in seconds using Boost - c++

I usually seed my RNG by the following time, obtained by a call to time.h
#include <iostream>
#include <time.h>
using namespace std;
int main()
{
cout << static_cast<unsigned int>(time(0)) << endl;
return 0;
}
Is there an equivalent to static_cast<unsigned int>(time(0)) in the Boost-library?

You can get the time using boost::posix_time. See this SO question. Ex:
boost::posix_time::time_duration diff = tick - now;
diff.total_milliseconds();
You can also use the C++11 chrono, if you can use C++11. Ex:
int elapsed_milliseconds = std::chrono::duration_cast<std::chrono::milliseconds>(end-start).count();
With these two methods, you can get the number of milliseconds from the start of the day, and then assign it to your seed.

Related

Converting time in milliseconds since epoch to time in yy-dd-hh-ss format

I have a bunch of tasks which are in the order of microseconds, the below code prints only until seconds (Thu Oct 21 12:48:20 2021) so comparing the values of start and finish always ends up giving 0. I want to be able to compare in the order of milliseconds and microseconds. Is there a function to help with this?
Also, is there a way to convert uint64_t current1 = std::chrono::system_clock::now().time_since_epoch().count(); to time_t to print out the current time based on the count()?
const auto p1 = std::chrono::system_clock::now();
std::time_t now = std::chrono::system_clock::to_time_t(p1);
std::cout << "now: " << std::ctime(&now);
I recommend skipping the C timing API entirely. It is error-prone and doesn't handle sub-second precision.
If UTC (as opposed to local time) is ok, then there is a header-only, open-source preview of C++20 that works with C++11/14/17:
#include "date/date.h"
#include <chrono>
#include <iostream>
int
main()
{
using date::operator<<;
const auto p1 = std::chrono::system_clock::now();
std::cout << "now: " << p1 << '\n';
}
Output:
now: 2021-10-21 20:28:15.754423
To port the above program to C++20 (which is already shipping in the latest Visual Studio), just drop the #include "date/date.h" and using date::operator<<;.
If you need local time, that can be also be had in C++20 (shipping in VS), but the open-source preview of C++20 is no longer header only. There exists one source file that needs to be compiled, and depending on your needs, might require a download of the IANA tz database.
#include "date/tz.h"
#include <chrono>
#include <iostream>
int
main()
{
using namespace date;
using namespace std::chrono;
const auto p1 = system_clock::now();
std::cout << "now: " << zoned_time{current_zone(), p1} << '\n';
}
Output:
now: 2021-10-21 16:28:15.754423 EDT
The above syntax assumes C++17. For C++11/14 the template parameter for zoned_time needs to be specified: zoned_time<system_clock::duration>.
The above program ports to C++20 by dropping #include "date/tz.h" and using namespace date;.
In either program you can truncate to millisecond precision with:
const auto p1 = floor<milliseconds>(system_clock::now());
time_t is usually an integer specifying (whole) seconds.
You could get the millseconds by subtracting the whole-second time_t from now:
auto ms = std::chrono::duration_cast<std::chrono::milliseconds>(
p1 - std::chrono::system_clock::from_time_t(now)).count();
or using operator%:
auto ms = std::chrono::time_point_cast<std::chrono::milliseconds>p1)
.time_since_epoch() % std::chrono::seconds(1);
std::cout << ms.count();
Example how you could do the formatting:
#include <chrono>
#include <iostream>
#include <iomanip>
int main() {
using Clock = std::chrono::system_clock;
using Precision = std::chrono::milliseconds;
auto time_point = Clock::now();
// extract std::time_t from time_point
std::time_t t = Clock::to_time_t(time_point);
// output the part supported by std::tm
std::cout << std::put_time(std::localtime(&t), "%FT%T."); // select format here
// get duration since epoch
auto dur = time_point.time_since_epoch();
// extract the sub second part from the duration since epoch
auto ss =
std::chrono::duration_cast<Precision>(dur) % std::chrono::seconds{1};
// output the millisecond part
std::cout << std::setfill('0') << std::setw(3) << ss.count();
}

c++ chrono Clock in HH:MM:SS when it needs to be in seconds.milliseconds

So right now, the code im using is
using std::chrono::system_clock;
std::time_t tt = system_clock::to_time_t (system_clock::now());
struct std::tm * ptm = std::localtime(&tt);
std::cout << "Current time: " << std::put_time(ptm,"%X") << '\n';
std::this_thread::sleep_for (std::chrono::seconds(7));
It is simple in that this is in a loop, and chrono sleep_for delays the system for however many seconds.
The problem is that it is in the HH:MM:SS format when I really need seconds.milliseconds to show the system clock transaction time. How would I do this? I really just need someone to explain the code, why is it making a struct? And what should I do to change the format? Thanks!
I've got two answers for you:
How to do this next year (in C++20), which isn't implemented today, and
How you can do it today with some minor syntax changes and an open-source 3rd party library.
First 1:
#include <chrono>
#include <iostream>
#include <thread>
int
main()
{
using namespace std::chrono;
auto tp = system_clock::now();
while (true)
{
zoned_time zt{current_zone(), floor<milliseconds>(system_clock::now())};
cout << "Current time: " << std::format("{:%T}", zt) << '\n';
tp += 7s;
std::this_thread::sleep_until (tp);
}
}
This creates a local time using the computer's currently set time zone, with a precision of milliseconds. And then just prints it out with the desired format (%T). I'm using sleep_until instead of sleep_for so that each iteration of the loop doesn't drift off of the desired 7s interval due to loop overhead.
Second 2:
Nobody has C++20 chrono yet, but you can approximate it today with Howard Hinnant's free open source date/time library:
#include "date/tz.h"
#include <chrono>
#include <iostream>
#include <thread>
int
main()
{
using namespace date;
using namespace std::chrono;
auto tp = system_clock::now();
while (true)
{
zoned_time zt{current_zone(), floor<milliseconds>(system_clock::now())};
cout << "Current time: " << format("%T", zt) << '\n';
tp += 7s;
std::this_thread::sleep_until (tp);
}
}
The difference is that the format statement is slightly different, and the library lives in namespace date instead of namespace std::chrono. And there's an extra header to include. And some installation is required to handle the time zones.
If you're happy with a UTC time stamp, instead of a local time stamp, then you can use a header-only version of the same library like this (no installation required):
#include "date/date.h"
#include <iostream>
#include <thread>
int
main()
{
auto tp = std::chrono::system_clock::now();
while (true)
{
using namespace date;
using namespace std::chrono;
std::cout << "Current time: "
<< format("%T", floor<milliseconds>(system_clock::now())) << '\n';
tp += 7s;
std::this_thread::sleep_until (tp);
}
}

Convert nanoseconds (since midnight) to printable time?

I have a uint64_t representing the number of nanoseconds since midnight. Would std::chrono allow me to convert this into a meaningful "time", relatively simply?
Also, how would I do it if I have the time since epoch?
For example in such a format:
14:03:27.812374923
And same situation, but when given nanoseconds since epoch? (in case the answer is significantly different)
You could use Howard Hinnant's, free, open-source, header-only library to do this:
#include "date.h"
#include <cstdint>
#include <iostream>
int
main()
{
using namespace std;
using namespace std::chrono;
using namespace date;
uint64_t since_midnight = 50607812374923;
cout << make_time(nanoseconds{since_midnight}) << '\n';
uint64_t since_epoch = 1499522607812374923;
cout << sys_time<nanoseconds>{nanoseconds{since_epoch}} << '\n';
}
This outputs:
14:03:27.812374923
2017-07-08 14:03:27.812374923
Or did you need to take leap seconds into account for since_epoch?
cout << utc_time<nanoseconds>{nanoseconds{since_epoch}} << '\n';
2017-07-08 14:03:00.812374923
For this latter computation, you'll need "tz.h" documented here, and this library is not header only.

boost ptime is thread safe or not?

I try to find a thread-safe way to get local time. From boost example, I got this:
#include "boost/date_time/posix_time/posix_time.hpp"
#include <iostream>
int
main()
{
using namespace boost::posix_time;
using namespace boost::gregorian;
//get the current time from the clock -- one second resolution
ptime now = second_clock::local_time();
//Get the date part out of the time
date today = now.date();
date tommorrow = today + days(1);
ptime tommorrow_start(tommorrow); //midnight
//iterator adds by one hour
time_iterator titr(now,hours(1));
for (; titr < tommorrow_start; ++titr) {
std::cout << to_simple_string(*titr) << std::endl;
}
time_duration remaining = tommorrow_start - now;
std::cout << "Time left till midnight: "
<< to_simple_string(remaining) << std::endl;
return 0;
}
But I didn't know if it can be used in multi-threading environment?
Yes, of your platform has support for it:
Date-time now uses reentrant POSIX functions on those platforms that support them when BOOST_HAS_THREADS is defined.
From here
BOOST_HAS_THREADS is basically always defined these days. You can check your platform's POSIX support if you doubt things.

How to get higher precision (fractions of a second) in a printout of current time?

I've tried a couple methods to print out time from the system_clock but I can't get anything other than whole seconds:
system_clock::time_point now = system_clock::now();
std::time_t now_c = system_clock::to_time_t(now);
std::cout<<ctime(&now_c);
std::cout<<std::put_time(std::localtime(&now_c), "%T")<<" ";
Does the now() function actually hold high precision data, or is that I just can't find the function that extracts that information for printing?
Note: I am not looking to calculate a time interval. I want the current time with fractions of a second, and to print it out via cout. I just can't find a way to do this.
And I know about std::chrono::high_resolution_clock but also see no way to print out its now(). Additionally, the setprecision function has no effect on the output of put_time or ctime.
I've been getting answers that do not actually address this question.
You can do the following:
#include <chrono>
#include <ctime>
#include <iostream>
#include <string>
std::string GetLocalTime() {
auto now(std::chrono::system_clock::now());
auto seconds_since_epoch(
std::chrono::duration_cast<std::chrono::seconds>(now.time_since_epoch()));
// Construct time_t using 'seconds_since_epoch' rather than 'now' since it is
// implementation-defined whether the value is rounded or truncated.
std::time_t now_t(
std::chrono::system_clock::to_time_t(
std::chrono::system_clock::time_point(seconds_since_epoch)));
char temp[10];
if (!std::strftime(temp, 10, "%H:%M:%S.", std::localtime(&now_t)))
return "";
return std::string(temp) +
std::to_string((now.time_since_epoch() - seconds_since_epoch).count());
}
int main() {
std::cout << GetLocalTime() << '\n';
return 0;
}
The existing answer is great, but it misses the leading zeros on the fractional part of the seconds, so 21:10:30.01 would be returned as 21:10:30.1
I don't have the rep to comment and my edit was rejected, so here's a fixed version:
#include <chrono>
#include <ctime>
#include <iostream>
#include <string>
std::string GetLocalTime() {
auto now(std::chrono::system_clock::now());
auto seconds_since_epoch(
std::chrono::duration_cast<std::chrono::seconds>(now.time_since_epoch()));
// Construct time_t using 'seconds_since_epoch' rather than 'now' since it is
// implementation-defined whether the value is rounded or truncated.
std::time_t now_t(
std::chrono::system_clock::to_time_t(
std::chrono::system_clock::time_point(seconds_since_epoch)));
char temp[10];
if (!std::strftime(temp, 10, "%H:%M:%S.", std::localtime(&now_t)))
return "";
std::string nanoseconds = std::to_string(
(std::chrono::duration<long long, std::nano>(
now.time_since_epoch() - seconds_since_epoch)).count());
return std::string(temp) + std::string(9-nanoseconds.length(),'0') + nanoseconds;
}
int main() {
std::cout << GetLocalTime() << '\n';
return 0;
}
Try std::chrono::high_resolution_clock.
(I think its c++11 only)