[C]LinuxでCプログラムの処理時間を計測する方法いくつか その3

2015年9月14日月曜日

C linux unix

移植性は低いかもしれないけど、最近のLinuxでは最もよさそうな関数が以下となる。
Linuxのバージョンや他のUnixシステムでは使えない可能性もある。

[clock_gettime関数]
#include <time.h>
int clock_gettime(clockid_t clk_id, struct timespec *tp);

この関数ではその1、その2と違い、clk_id引数でどういった時間を取得するかを指定する。
よく使いそうなのは以下だろう。

CLOCK_MONOTONIC:ある時点からの単調増加のクロック数。NTP等の時間調整の影響を受ける。
CLOCK_MONOTONIC_RAW:ある時点からの単調増加のクロック数。NTP等の時間調整の影響を受けない。
CLOCK_PROCESS_CPUTIME_ID: CPU による高分解能のプロセス毎のタイマ。

timespec構造体は秒とナノ秒を保持している。

例:
    struct timespec start;
    struct timespec end;

    clock_gettime(CLOCK_MONOTONIC, &start);
    // 計測したい処理...
    clock_gettime(CLOCK_MONOTONIC, &end);

    long long elapsed = 1000 * 1000 * 1000 * (end.tv_sec - start.tv_sec);
    elapsed += end.tv_nsec - start.tv_nsec;

[getrusage関数]
#include <sys/time.h>
#include <sys/resource.h>
int getrusage(int who, struct rusage *usage);

こちらは時間だけでなく、リソースの使用状況を取得する関数となる。
who引数で何のリソースの使用状況を取得するかを指定する。
whoに指定する値は以下がある。

RUSAGE_SELF:プロセスの消費リソース。
RUSAGE_CHILDREN:子プロセスまで含めた消費リソース。
RUSAGE_THREAD:スレッドの消費リソース。

rusage構造体はユーザCPU使用時間やシステムCPU使用時間以外にも様々なリソースの使用状況を保持している。

例:
    struct rusage start;
    struct rusage end;
    int i;

    getrusage(RUSAGE_SELF, &start);
    // 計測したい処理...
    getrusage(RUSAGE_SELF, &end);

    long long elapsed = 1000 * 1000 * (end.ru_utime.tv_sec - start.ru_utime.tv_sec);
    elapsed += end.ru_utime.tv_usec - start.ru_utime.tv_usec;

その1、その2と同様に消費したリソース量を計測したいのか、実時間を計測したいのかによって使い分ける必要があるだろう。