hello, i’m new to programming in i’m trying to solve this exercise in C, basically it’s the amount of passed hours between the start of a game and it’s end, if the game started at 16 and ended at 2 the result is a game with 10 hours(in different days) i know i can to it more manually, but i wanted to somehow use the <time.h> to learn how to use a header etc, can someone help me?, thank you all
You save the unix timestamp at the beginning of the game and the end of the game (or use the current one). With this timestamps you can use functions to calculate length etc. For example https://cplusplus.com/reference/ctime/difftime/ You then can convert those into a better format. More info here https://cplusplus.com/reference/ctime/
Also chatgpt could help in those cases, if you don’t want to wait for a answer on here :P
I think the is the most accurate solution,
clock()
as suggested by another answer may overflow, but this only suffers from potential precision problems with double, but you’d have to wait for an incredibly long time for this to become significant.
The thing is to take 2 time stamps: one at the beginning and one at the end of the game. Then you subtract the beginning value from the end to get the elapsed time.
In terms of
<time.h>
, you probably want to callclock()
to get these time stamps.clock_t beginTime = clock();
And later:
clock_t endTime = clock(); double elapsed = (double)(endTime - beginTime) / CLOCKS_PER_SEC;
That would give you the time in seconds, which you could make into hours by dividing it further by 3600.
(Note: It’s been a long time since I’ve programmed straight C so I may be off on something here? In C++, you would want to use
std::chrono::steady_clock::now()
to get your time stamps, even thoughclock()
still exists.)This is correct, however it is important to note that the C standard allows arbitrary values at the beginning of the program. The manpage does a better job explaining it.
Doing a bit of research, it looks like the POSIX
time_t time(time_t *dest)
function (man) is available on Windows (see here). So I would recommend that overclock_t clock(void)
as it will operate more consistently across platforms.The arbitrary values at the beginning of the program is the reason you want to measure a difference rather than an absolute time. Like you don’t want to simply go
(double)clock() / CLOCKS_PER_SEC
at the end of the program. That would only work if you knew for certain that the clock started at 0 on program launch. Some operating systems may ensure this. Others may only zero it when the CPU is booted, for example. So it’s just not safe to work with absolute times, but differences between time stamps should still behave consistently across platforms.Now, the problem with
time()
and friends is they represent the kind of time displayed by your computer. In most cases, this should work fine, but occasionally, the OS may adjust this time for a number of reasons. It may be jumping ahead or back due to daylight savings, for example, or adding/losing some seconds as it syncs the computer clock to an NTP server someplace. What you want to use to avoid such shenanigans in measuring time elapsed is a steady clock which ticks along regardless of what the OS decides to do. I thinkclock()
is your best bet for that in plain C? (It also may have a higher resolution thantime()
, though that’s not super important if you’re only worried about counting hours.)Using
clock()
solely for delta values is absolutely a valid approach, as stated. The issue is thatclock_t
may not be large enough of some systems to safely keep you from an overflow, especially with arbitrary values. Additionally, some systems will include the time children processes were alive in subsequentclock()
calls, furthering possible confusion. These are reasons why I would avoidclock()
in favor oftime()
, even though your concerns are absolutely valid.At the end of the day you have to determine which style of unpredictability you want to work around. Dealing with the
times()
,clock()
, andclock_gettime()
class of functions opens you up to managing what the kernel considers time passed, and what is accumulated vs what is not. While usingtime()
can have shifts in time according to upstream NTP servers, as well as daylight savings time.I would also make the argument that if an NTP server is adjusting your time, it is most likely more accurate than what your internal clock (CMOS or otherwise) was counting, and is worth following.
Okay, I’ve read up on this a bit an you raise some valid points.
For whatever reason, posix has decided that
CLOCKS_PER_SEC
must be exactly 1000000 on every system that wants to comply. That doesn’t leave much room on a 32-bit system for maximum clock duration. It will wrap around well before the 10 hours the OP was giving by example.The other is I gather on some systems,
clock()
may be measuring the uptime of a particular process, which is not necessarily the same as real world time in multicore environments. (Fwiw I’m on a Mac where I don’t think it works that way? You would need some special apis to get that kind of info.)I’m trying to think of the last time I programmed straight C and used
time.h
and the like. It was probably in developing scientific instrumentation? iirc the clock in that case was keyed to the VBL refresh of the display, meaningCLOCKS_PER_SEC
would have been something like 60 Hz. And I doubttime()
would have yielded any useful value. I wonder what the OP’s use case is?Most of my hobby programming is in ANSI C and C99, so I’m unfortunately far too aware of the weird and counter-intuitive things the C and POSIX standards say. :P
clock()
is fantastic for sub-second timings, such as deltatimes in games, or peripheral synchronization, which matches the use case you mention very well. I recommendedtime()
over it as OP’s use case is for calculating the amount of hours a user has had their software open, and unix timestamps are the perfect mechanism to do that in my opinion.
Take 10 minutes to watch this video, then follow his advice. get a library that handles time and date and use it.