Вы можете использовать эту функцию, которую я написал. Вы вызываете GetTimeMs64 ()
, и он возвращает количество миллисекунд, прошедших с эпохи unix с использованием системных часов - точно так же, как time (NULL)
, за исключением миллисекунд.
Он работает как в Windows, так и в Linux; это потокобезопасный.
Обратите внимание, что степень детализации для окон составляет 15 мс; в Linux это зависит от реализации, но обычно это также 15 мс.
#ifdef _WIN32
#include <Windows.h>
#else
#include <sys/time.h>
#include <ctime>
#endif
/* Remove if already defined */
typedef long long int64; typedef unsigned long long uint64;
/* Returns the amount of milliseconds elapsed since the UNIX epoch. Works on both
* windows and linux. */
uint64 GetTimeMs64()
{
#ifdef _WIN32
/* Windows */
FILETIME ft;
LARGE_INTEGER li;
/* Get the amount of 100 nano seconds intervals elapsed since January 1, 1601 (UTC) and copy it
* to a LARGE_INTEGER structure. */
GetSystemTimeAsFileTime(&ft);
li.LowPart = ft.dwLowDateTime;
li.HighPart = ft.dwHighDateTime;
uint64 ret = li.QuadPart;
ret -= 116444736000000000LL; /* Convert from file time to UNIX epoch time. */
ret /= 10000; /* From 100 nano seconds (10^-7) to 1 millisecond (10^-3) intervals */
return ret;
#else
/* Linux */
struct timeval tv;
gettimeofday(&tv, NULL);
uint64 ret = tv.tv_usec;
/* Convert from micro seconds (10^-6) to milliseconds (10^-3) */
ret /= 1000;
/* Adds the seconds (10^0) after converting them to milliseconds (10^-3) */
ret += (tv.tv_sec * 1000);
return ret;
#endif
}
Лучше выполнить внутренний цикл несколько раз с синхронизацией производительности только один раз и усреднить, разделив повторения внутреннего цикла, чем выполнять все это (цикл + синхронизация производительности) несколько раз и усреднить. Это снизит накладные расходы на код времени производительности по сравнению с вашим фактическим профилированным разделом.
Оберните ваши вызовы таймера для соответствующей системы. Для Windows QueryPerformanceCounter довольно быстр и «безопасен» в использовании.
Вы можете использовать «rdtsc» на любом современном ПК с X86, но могут возникнуть проблемы на некоторых многоядерных машинах (переключение ядра может изменить таймер) или если у вас включен какой-то шаг-шаг.
Я предлагаю использовать стандартные библиотечные функции для получения информации о времени из системы.
Если вы хотите более точное разрешение, выполните больше итераций выполнения. Вместо того, чтобы запускать программу один раз и получать образцы, запустите ее 1000 или более раз.
У меня есть еще один рабочий пример, который использует микросекунды (UNIX , POSIX и т. Д.)
#include <sys/time.h>
typedef unsigned long long timestamp_t;
static timestamp_t
get_timestamp ()
{
struct timeval now;
gettimeofday (&now, NULL);
return now.tv_usec + (timestamp_t)now.tv_sec * 1000000;
}
...
timestamp_t t0 = get_timestamp();
// Process
timestamp_t t1 = get_timestamp();
double secs = (t1 - t0) / 1000000.0L;
Вот файл, в котором мы это закодировали:
https://github.com/arhuaco/junkcode/blob/master/emqbit-bench/bench.c
Windows предоставляет функцию QueryPerformanceCounter (), а Unix имеет gettimeofday () Обе функции могут измерять разницу минимум в 1 микросекунду.
Оператор запятой привязывается ниже назначения, поэтому выражение
inhi=1,0
задает для inhi
значение 1
, а затем возвращает 0
. Аналогично
inhi=0,1
набор inhi
- 0
и возвращает 1
. Все это эквивалентно
if(y[0] > y[1]) {
inhi = 1;
ihi = 0;
} else {
inhi = 0;
ihi = 1;
}
Я бы предложил переписать так, если можно. inhi
и ihi
, по-видимому, имеют одну и ту же цель (в этом утверждении), и сочетание троичного оператора (?:
) и оператора запятой, которое вы имеете, дает им различный вес.
Это означает следующее:
if (y[0]>y[1])
{
inhi = 1;
ihi = 0;
} else {
inhi = 0;
ihi = 1;
}
Или написанный другим способом (в C++):
inhi = (y[0]>y[1]);
ini = !inhi;
-121--2681513- В некоторых программах я использовал RDTS для этой цели. RDTSC - это не время, а количество циклов с момента запуска процессора. Вы должны откалибровать его в вашей системе, чтобы получить результат в секунду, но это действительно удобно, когда вы хотите оценить производительность, еще лучше использовать количество циклов непосредственно, не пытаясь изменить их обратно на секунды.
(ссылка выше на французскую страницу википедии, но она имеет образцы кода C++, английская версия - здесь )
boost :: timer , вероятно, даст вам столько точности, сколько вам нужно. Это далеко не так точно, чтобы сказать вам, сколько времени займет a = a + 1;
, но, мне кажется, зачем вам нужно рассчитывать время для того, что занимает пару наносекунд?