C 言語の gettimeofday 関数を使用する
この記事では、C 言語の gettimeofday
関数を使ってコードブロック内の経過時間を計算する方法をいくつか説明します。
C 言語でコードブロック内の経過時間を計算するために gettimeofday
関数を使用する
関数 gettimeofday
は POSIX に準拠した関数であり、マイクロ秒単位の精度で現在の時刻を取得します。この関数は 2つの引数をとり、1つは struct timeval
型のもので、もう 1つは struct timezone
型のものです。しかし、timezone
構造体は減価償却されているので、代わりに NULL
を渡すべきです。一方、timeval
構造体にはエポックからの経過秒数とマイクロ秒数を表す tv_sec
と tv_usec
の 2つのメンバがあります。以下のサンプルコードは、単一の関数の実行時間を計測する方法を示しています - loopFunc
。
一般的に、測定すべきコードブロックを、ブロックの前と後の 2 回の gettimeofday
の呼び出しで囲む必要があります。2 回目の gettimeofday
の呼び出しが成功したら、カスタム定義の関数 time_diff
を使って時間差を計算することができます。これは両方の timeval
構造体の値を受け取り、その差を秒に変換します。
#include <stdio.h>
#include <stdlib.h>
#include <sys/time.h>
#include <time.h>
#define NUM 1000000
#define NUM2 10000000
float time_diff(struct timeval *start, struct timeval *end) {
return (end->tv_sec - start->tv_sec) + 1e-6 * (end->tv_usec - start->tv_usec);
}
void loopFunc(size_t num) {
int tmp = 0;
for (int i = 0; i < num; ++i) {
tmp += 1;
}
}
int main() {
struct timeval start;
struct timeval end;
gettimeofday(&start, NULL);
loopFunc(NUM);
gettimeofday(&end, NULL);
printf("loopFunc(%d) time spent: %0.8f sec\n", NUM, time_diff(&start, &end));
gettimeofday(&start, NULL);
loopFunc(NUM2);
gettimeofday(&end, NULL);
printf("loopFunc(%d) time spent: %0.8f sec\n", NUM2, time_diff(&start, &end));
exit(EXIT_SUCCESS);
}
出力:
loopFunc(1000000) time spent: 0.00221000 sec
loopFunc(10000000) time spent: 0.02184500 sec
関数 clock_gettime
を用いて C 言語のコードブロック内の経過時間を計算する
代わりに、gettimeofday
関数はすでに廃止されているので、代わりに clock_gettime
関数を利用することをお勧めします。後者の関数は、最初のパラメータに指定した異なるクロックからタイミングデータを取得することができます。共通のクロックの種類は、いわゆるウォールクロックの時間を計測するシステム全体のクロックで、マクロ CLOCK_REALTIME
で識別されます。タイミング値は timespec
構造体に格納され、エポックから渡された秒数とナノ秒を表す 2つのメンバで構成されます。呼び出し元は timespec
オブジェクトを事前に宣言し、そのアドレスを clock_gettime
関数に渡すことに注意してください。
#include <stdio.h>
#include <stdlib.h>
#include <sys/time.h>
#include <time.h>
#define NUM 1000000
#define NUM2 10000000
float time_diff2(struct timespec *start, struct timespec *end) {
return (end->tv_sec - start->tv_sec) + 1e-9 * (end->tv_nsec - start->tv_nsec);
}
void loopFunc(size_t num) {
int tmp = 0;
for (int i = 0; i < num; ++i) {
tmp += 1;
}
}
int main() {
struct timespec start2;
struct timespec end2;
clock_gettime(CLOCK_REALTIME, &start2);
loopFunc(NUM);
clock_gettime(CLOCK_REALTIME, &end2);
printf("loopFunc(%d) time spent: %0.8f sec\n", NUM,
time_diff2(&start2, &end2));
clock_gettime(CLOCK_REALTIME, &start2);
loopFunc(NUM2);
clock_gettime(CLOCK_REALTIME, &end2);
printf("loopFunc(%d) time spent: %0.8f sec\n", NUM2,
time_diff2(&start2, &end2));
exit(EXIT_SUCCESS);
}
出力:
loopFunc(1000000) time spent: 0.00221000 sec
loopFunc(10000000) time spent: 0.02184500 sec