SDL vs std::chrono
for Timing
What are the advantages of using std::chrono
over SDL's timing functions?
While SDL's timing functions are useful, std::chrono
from the C++ standard library offers several advantages:
Portability
std::chrono
is part of the C++ standard library, making it available on any platform with a C++11 (or later) compliant compiler. This means you can use the same timing code across different projects, even those not using SDL.
Type Safety
std::chrono
provides strong type safety through its use of templates. This helps prevent errors related to unit conversions:
#include <chrono>
#include <iostream>
int main() {
using namespace std::chrono;
auto start{high_resolution_clock::now()};
// Simulate some work
for (int i{0}; i < 1000; ++i) {
std::cout << "Working...\n";
}
auto end{high_resolution_clock::now()};
auto durationMs{
duration_cast<milliseconds>(end - start)};
auto durationUs{
duration_cast<microseconds>(end - start)};
std::cout << "Duration in milliseconds: " <<
durationMs.count() << "ms\n";
std::cout << "Duration in microseconds: " <<
durationUs.count() << "us\n";
return 0;
}
Working...
Working...
Working...
Duration in milliseconds: 32ms
Duration in microseconds: 32581us
Flexibility
std::chrono
offers a range of clock types and duration representations, allowing you to choose the most appropriate for your needs:
#include <chrono>
#include <iostream>
int main() {
using namespace std::chrono;
// High-resolution clock (similar
// to SDL_GetPerformanceCounter)
auto highResStart{
high_resolution_clock::now()};
// System clock (wall clock time)
auto sysClockStart{system_clock::now()};
// Steady clock (monotonic time)
auto steadyStart{steady_clock::now()};
// Simulate some work
for (int i{0}; i < 1000; ++i) {
std::cout << "Working...\n";
}
auto highResEnd{high_resolution_clock::now()};
auto sysClockEnd{system_clock::now()};
auto steadyEnd{steady_clock::now()};
std::cout << "High-res duration: "
<< duration_cast<nanoseconds>(
highResEnd - highResStart).count()
<< "ns\n";
std::cout << "System clock duration: "
<< duration_cast<microseconds>(
sysClockEnd - sysClockStart).count()
<< "us\n";
std::cout << "Steady clock duration: "
<< duration_cast<nanoseconds>(
steadyEnd - steadyStart).count()
<< "ns\n";
return 0;
}
Working...
Working...
Working...
High-res duration: 36367300ns
System clock duration: 36367us
Steady clock duration: 36368000ns
Integration with Standard Library
std::chrono
integrates well with other parts of the C++ standard library, such as <thread>
for sleep operations:
#include <chrono>
#include <iostream>
#include <thread>
int main() {
using namespace std::chrono;
auto start{high_resolution_clock::now()};
std::this_thread::sleep_for(
milliseconds(100));
auto end{high_resolution_clock::now()};
std::cout << "Slept for " << duration_cast<
milliseconds>(end - start).count()
<< "ms\n";
return 0;
}
Slept for 107ms
While SDL's timing functions are straightforward and work well within SDL-based projects, std::chrono
offers more flexibility, type safety, and integration with the broader C++ ecosystem.
In many cases, using std::chrono
can lead to more robust and maintainable code, especially in projects that aren't exclusively tied to SDL.
High-Resolution Timers
Learn to measure time intervals with high accuracy in your games