Linux講座にようこそ。このページは「C言語プログラミング入門 - 第14章.ライブラリ関数 - 日付および時間ライブラリ」です。

C言語プログラミング入門

14. ライブラリ関数(25/36) - 日付および時間ライブラリ(3/3)

14.38 日時を文字形式に変換・編集関数

14.38.1 ctime関数

ctime関数は紀元からの経過秒数(1970年1月1日00:00:00 UTCからの経過秒数)を文字形式の日時に変換します。日時はローカル時間に変換しますので明示的に変換する必要は有りません。

変換結果は英語表現で次のような形式です。最後に改行文字が付加されますので注意してください。

曜日 月 日 時:分:秒 西暦\n

【表14-5-7】 ctime関数
形式#include <time.h>
char *ctime(const time_t *timep);
返り値文字形式の日時を返します。エラーの場合はNULLを返します。
引数
const time_t *timep
紀元からの経過秒数を指定します。

14.38.2 asctime関数

asctime関数は日時構造体(tm構造体)から文字形式の日時に変換します。日時はローカル時間に変換しますので明示的に変換する必要は有りません。また、変換結果はctime関数と同じです。

【表14-5-8】 asctime関数
形式#include <time.h>
char *asctime(const struct tm *tm);
返り値文字形式の日時を返します。エラーの場合はNULLを返します。
引数
const struct tm *tm
日時構造体を指定します。

14.38.3 strftime関数

strftime関数は日時構造体(tm構造体)を書式に従い編集します。書式には表14-5-10の変換指定文字が使用できます。

【表14-5-9】 strftime関数
形式#include <time.h>
size_t strftime(char *s, size_t max, const char *format, const struct tm *tm);
返り値編集結果の文字数(ヌル文字は含まない)を返します。書式の内容により、0が返る可能性が有りますがエラーとは限りません。
引数
char *s
編集結果の日時を格納する文字列を指定します。
size_t max
編集結果の日時を格納する文字列(第1引数のs)の長さを指定します。
const char *format
編集のための書式を指定します。
const struct tm *tm
編集する日時情報を格納した日時構造体(tm構造体)を指定します。

書式には次の変換指定文字を指定します。変換指定文字以外の文字はそのまま編集結果に反映します。

【表14-5-10】 変換指定文字
変換指定文字意味
%a現在のロケールにおける曜日の省略名です。
%A現在のロケールにおける曜日の完全な名前です。
%b現在のロケールにおける月の省略名です。
%B現在のロケールにおける月の完全な名前です。
%c現在のロケールにおける一般的な日付・時刻の表記です。
%d日です。(01〜31)
%H24時間表記での時です。(00〜23)
%I12時間表記での時です。(01〜12)
%j年の初めから通算の日数です。(001〜366)
%m月です。(01〜12)
%M分です。(00〜59)
%p現在のロケールにおける「午前」と「午後」に相当する文字列です。英語の場合には'AM'または'PM'です。正午は午後、真夜中は午前として扱われます。
%S秒です。(00〜60)
%U年の初めからの通算の週数です。(00〜53)その年の最初の日曜日を第1週の始まりとして計算します。
%W年の初めからの通算の週数です。(00〜53)その年の最初の月曜日を第1週の始まりとして計算します。
%x現在のロケールにおける一般的な日付表記です。時刻は含みません。
%X現在のロケールにおける一般的な時刻表記です。日付は含みません。
%y西暦の下2桁(世紀部分を含まない年)です。(00〜99)
%Y世紀部分を含めた(4桁の)西暦年です。
%Zタイムゾーンまたは、ゾーン名または、それらの省略名です。

14.38.4 例題

ctime関数で英語表現の日時を表示し、strftime関数で日本語表現で日時を表示します。

#include <stdio.h>
#include <time.h>
#include <locale.h>

int main(void)
{
    time_t      timep;
    struct tm   *time_inf;
    char        buff[100];

    /* 紀元からの経過秒数を得る */
    timep = time(NULL);

    /* 英語表現の日時 */
    printf("ctime関数\n");
    printf("%s", ctime(&timep));

    /* ローカル標準時へ変換 */
    time_inf = localtime(&timep);
    /* ロケールの設定 */
    setlocale(LC_TIME, "ja_JP.UTF-8");
    printf("\nstrftime関数\n");
    /* 一般的な日時 */
    strftime(buff, sizeof(buff), "%c", time_inf);
    printf("%s\n", buff);
    /* 午前と午後及び、タイムゾーン */
    strftime(buff, sizeof(buff), "%x %p%X %Z", time_inf);
    printf("%s\n", buff);

    return 0;
}
$ date
2009年  8月 25日 火曜日 09:25:19 JST
$
$ ./ex14_5_2.prg
ctime関数
Tue Aug 25 09:25:21 2009

strftime関数
2009年08月25日 09時25分21秒
2009年08月25日 午前09時25分21秒 JST
$
16行目
紀元からの経過秒数をctime関数で英語表現の日時として表示します。
24行目
日時構造体の日時情報をstrftime関数で現在のロケールにおける一般的な日時表現に編集して表示します。
27行目
日時構造体の日時情報をstrftime関数で午前と午後及び、タイムゾーンを付加して表示します。

14.39 その他の関数

14.39.1 clock関数

clock関数はプログラムのCPU使用時間の近似値をclock_t単位の時間で取得します。秒単位でのCPU使用時間はCLOCKS_PER_SECで割ることで算出できます。また、clock_t単位の時間は桁あふれをする可能性がありますので注意してください。例えばCLOCKS_PER_SECが1000000である32ビットシステムでは、約72分毎に同じ値を返すことになります。

この関数の標準規格では、最初の呼び出しではどのような値が返ってきても構わないことになっています。移植性を確保するためには、計測開始時にclock関数を呼び出してCPU使用時間を取得しておき、この値を差し引くことで実際のCPU使用時間を求めた方がよいでしょう。

【表14-5-11】 clock関数
形式#include <time.h>
clock_t clock(void);
返り値clock_t単位のCPU使用時間を返します。エラーの場合は((clock_t) -1)を返します。
引数 ありません。

14.39.2 difftime関数

difftime関数は2つの紀元からの経過秒数から経過時間を算出します。

【表14-5-12】 difftime関数
形式#include <time.h>
double difftime(time_t time1, time_t time0);
返り値秒単位の経過時間を返します。
引数
time_t time1
計測開始時刻を紀元からの経過秒数で指定します。
time_t time0
計測終了時刻を紀元からの経過秒数で指定します。

14.39.3 例題

プログラムのCPU使用時間と実行時間(経過時間)を表示します。

  1. #include <stdio.h>
  2. #include <time.h>
  3. #include <unistd.h>
  4. #define MAXLOOP 100000000
  5.  
  6. int main(void)
  7. {
  8.     time_t      start_timep;
  9.     clock_t     start_cpu;
  10.     int         loop_1, loop_2;
  11.  
  12.     /* 開始時刻を得る */
  13.     start_timep = time(NULL);
  14.     /* CPU使用時間を取得 */
  15.     start_cpu = clock();
  16.  
  17.     /* CPUを消費 */
  18.     for (loop_1 = 1; loop_1 <= 5; ++loop_1)
  19.     {
  20.         for (loop_2 = 0; loop_2 < MAXLOOP; ++loop_2)
  21.             ;
  22.         /* 休憩 */
  23.         sleep(1);
  24.     }
  25.  
  26.     /* CPU使用時間の表示 */
  27.     printf("CPU使用時間:%.1f秒\n",
  28.          (double)(clock() - start_cpu) / (double)CLOCKS_PER_SEC);
  29.  
  30.     /* 経過時間の表示 */
  31.     printf("経過時間:%.1f秒\n", difftime(time(NULL), start_timep));
  32.  
  33.     return 0;
  34. }
$ ./ex14_5_3.prg
CPU使用時間:1.1秒
経過時間:6.0秒
$
13行目
実行開始時刻をtime関数で求めます。
15行目
実行開始時点のCPU使用時間をclock関数で求めます。
28行目
この時点でのCPU使用時間から実行開始時点のCPU使用時間を引いて、CPU使用時間を求めます。時間はCLOCKS_PER_SECで除算して秒単位で求めます。
31行目
この時点での時刻と実行開始時刻からdifftime関数で実行時間(経過時間)を求めます。