Как получить время выполнения программы в миллисекундах на языке Си?



В настоящее время я получаю время выполнения моей программы в секундах, вызывая:

time_t startTime = time(NULL);
//section of code
time_t endTime = time(NULL);
double duration = difftime(endTime, startTime);

Можно ли получить время стены в миллисекундах ? Если да, то как?

135   6  

6 ответов:

Если вы находитесь на машине POSIX-ish, используйте gettimeofday() вместо этого; это дает вам разумную переносимость и разрешение микросекунды.

Несколько более эзотерическим, но также и в POSIX, является clock_gettime() функция, которая дает вам разрешение наносекунды.

Во многих системах вы найдете функцию ftime(), которая фактически возвращает вам время в секундах и миллисекундах. Однако он больше не входит в единую спецификацию Unix (примерно то же, что и POSIX). Тебе нужно ... заголовок <sys/timeb.h>:
struct timeb mt;
if (ftime(&mt) == 0)
{
     mt.time ... seconds
     mt.millitime ... milliseconds
}

Это восходит к версии 7 (или 7-му изданию) Unix, по крайней мере, поэтому она была очень широко доступна.

У меня также есть заметки в моем подсекундном коде таймера на times() и clock(), которые снова используют другие структуры и заголовки. У меня также есть заметки о Windows, использующей clock() с 1000 тактов в секунду (время миллисекунды), и более старый интерфейс GetTickCount(), который отмечен как необходимый на Windows 95, но не на NT.

Если вы можете сделать это вне самой программы, в linux вы можете использовать команду time (time ./my_program).

Недавно я написал пост в блоге, который объясняет, Как получить время в миллисекундах кросс-платформенным .

Он будет работать как time (NULL), но будет возвращать количество миллисекунд вместо секунд из эпохи unix как в windows, так и в linux.

Вот код

#ifdef WIN32
#include <Windows.h>
#else
#include <sys/time.h>
#include <ctime>
#endif

/* Returns the amount of milliseconds elapsed since the UNIX epoch. Works on both
 * windows and linux. */

int64 GetTimeMs64()
{
#ifdef WIN32
 /* Windows */
 FILETIME ft;
 LARGE_INTEGER li;
 uint64 ret;

 /* 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;

 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;
 uint64 ret;

 gettimeofday(&tv, NULL);

 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
}

Вы можете изменить его, чтобы возвращать микросекунды вместо миллисекунд, если хотите.

Библиотека GLib с открытым исходным кодом имеет систему GTimer, которая утверждает, что обеспечивает микросекундную точность. Эта библиотека доступна в Mac OS X, Windows и Linux. В настоящее время я использую его, чтобы сделать тайминги производительности на Linux, и он, кажется, работает идеально.

gprof, что является частью инструментария GNU, это вариант. В большинстве систем POSIX он будет установлен, и он доступен под Cygwin для Windows. Отслеживание времени самостоятельно с помощью gettimeofday() работает нормально, но это эквивалентно использованию инструкций print для отладки. Это хорошо, если вы просто хотите быстрого и грязного решения, но это не так элегантно, как использовать правильные инструменты.

Чтобы использовать gprof, необходимо указать параметр-pg при компиляции с gcc как в:

gcc -o prg source.c -pg

Тогда вы можете запустить gprof в сгенерированной программе следующим образом:

gprof prg > gprof.out

По умолчанию gprof генерирует общее время выполнения вашей программы, а также количество времени, затраченного на каждую функцию, количество раз, когда каждая функция была вызвана, среднее время, затраченное на каждый вызов функции, и аналогичную информацию.

Существует большое количество опций, которые можно задать с помощью gprof. Если вам интересно, вы можете найти дополнительную информацию на man-страницах или в Google.

В Windows используйте QueryPerformanceCounter и связанную с ним QueryPerformanceFrequency. Они не дают вам время, которое можно перевести в календарное время, поэтому, если вам это нужно, попросите время с помощью CRT API, а затем немедленно используйте QueryPerformanceCounter. Затем вы можете выполнить простое сложение / вычитание для вычисления календарного времени с некоторой ошибкой из-за времени, необходимого для последовательного выполнения API. Эй, это же компьютер, а ты чего ожидал???

    Ничего не найдено.

Добавить ответ:
Отменить.