曜日を取得するアルゴリズムは,ツェラーの公式 (Zeller's congruence) が有名ですが,ここでは time.h の mktime 関数を使用する方法を紹介します.
#include <time.h>
time_t mktime( struct tm *timeptr );
mktime 関数は 引数 timeptr が指す tm 構造体の内容を,暦時刻 (calendar time) の値に変換する関数です.
変換の際には,tm_wday 要素 (日曜日からの日数) と tm_yday要素 (1月1日からの日数) の元の値は無視され自動的に適切な値が格納されます.この "適切な値" というのがミソで,この性質を利用すると日付から曜日を求めることができます.
以下に mktime 関数を使用して,日付から曜日を取得するサンプルプログラムを示します.
/* header files */
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
/* functions */
int GetDayOfWeek(int year, int month, int day);
void DisplayWeek(int wday);
/* main */
int main(void) {
int year = 2009;
int month = 4;
int day = 20;
int week;
/* 日付の表示 */
printf("%d/%d/%d: ", year, month, day);
/* 曜日を求める */
week = GetDayOfWeek(year, month, day);
/* 曜日の表示 */
DisplayWeek(week);
return EXIT_SUCCESS;
}
/**
* 曜日を求める
* @param[in] year 年
* @param[in] month 月
* @param[in] day 日
* @return 曜日(0を日曜日とする. エラー時は-1を返す)
*/
int GetDayOfWeek(int year, int month, int day) {
struct tm time_in, *local;
time_t t;
/* 年月日を入力 */
time_in.tm_year = year - 1900; /* 年 */
time_in.tm_mon = month - 1; /* 月 */
time_in.tm_mday = day; /* 日 */
/* 時分秒曜日を適当に入力 */
time_in.tm_hour = 1; /* 時 (適当に入力) */
time_in.tm_min = 0; /* 分 (適当に入力) */
time_in.tm_sec = 0; /* 秒 (適当に入力) */
time_in.tm_wday = 0; /* 曜日 (適当に入力) */
time_in.tm_yday = 0; /* 1月1日からの日数 (適当に入力) */
/* mktime 関数で変換 */
if ( (t = mktime(&time_in) ) == (time_t)(-1) ) {
return -1;
}
/* 地方時に変換 */
local = localtime(&t);
return local->tm_wday;
}
/**
* 曜日を表示する
* @param[in] wday 曜日(0を日曜日とする)
*/
void DisplayWeek(int wday) {
char weeks[][16] = {
"日曜日",
"月曜日",
"火曜日",
"水曜日",
"木曜日",
"金曜日",
"土曜日"
};
printf("%s\n", weeks[wday]);
}
サンプルプログラムの実行結果は以下のようになります.
2009/4/20: 月曜日
たくさんあるC言語関連の書籍の中でも特に役に立った本です.よかったら参考にしてみてください.
C言語の実践的参考書.少々値段は張りますが初心者を脱しようとしている人は絶対に読むべきです.
文法だけでなく,コーディングスタイルやデバッグなど文字通り「実践的」なことが書かれているので非常にためになります.
オライリーの本は,読みにくい本が多いのですが本書はとても読みやすくオススメです.
ポインタの解説書としては最高の書籍です.
この1冊でポインタを完全に理解することができます.全くの初学者が読むには敷居が高いですが,入門書を読み終えた後に読むと非常に有益です.