いま、カレンダー(WEBサイトのですが)を作っているんだが、なんも考えずにphpのdate関数で書いてたら、当然だが対応できる限界があるというのに気付いた。
難しい事は他の親切なサイトに説明を譲るとして、とりあえず32bitの限界という事だろうか。
月のカレンダーを描画する時に、曜日を取得する必要があって、
何年何月の1日の曜日を取得したいって時に、こんな感じで取得する訳です。
$youbi = date("N",mktime(0,0,0,$month,1,$year))
で、date関数だと確か1904年くらいが限界な訳ですね。
とりあえず、そんな32bit環境とかphpの仕様とかに負けたくないので、
年月を渡して曜日を返す関数とか作ろうと思った訳ですが、これがハマった。
なんか意外とややこしくて、以下のような感じ。
function dayOfWeek($y,$m){
$addMonthElement = array(
"01" => 6,
"02" => 2,
"03" => 2,
"04" => 5,
"05" => 0,
"06" => 3,
"07" => 5,
"08" => 1,
"09" => 4,
"10" => 6,
"11" => 2,
"12" => 4
);
$yb = (((($y % 400 + floor($y % 400 / 4) - floor($y % 400 / 100)) % 7 + $addMonthElement[$m]) % 7) + 1) % 7;
if($yb==0){
$yb = 7;
}
return $yb;
}
配列にぶち込んであるパラメータが、なんでこうなるのか理解していません。
とりあえず、年月を渡すと正しい曜日(数値)を返すので、まぁよしとした。
ただ、この関数で西暦1年1月1日を求めると日曜日になってしまう。
ググッてみると、西暦1年1月1日は月曜日のようなんだな。
この計算式はグレゴリオ暦をもとにしていて、そもそもグレゴリオ暦ってのは16世紀から始まったもので、それ以前はユリウス暦(旧暦)だったらしく、15世紀以前はこの計算式通りにはいかないのかも知れない。この辺も大変ややこしいので理解できず。
また、もっと遡って紀元前とかも対応しようと思ったんだが、これがまたややこしい。
単純にそのままマイナス1していけば良いというものではなくて、
西暦1年の1年前は西暦0年ではなく、紀元前1年なんですね(当然)。
となると、上記関数のような計算では閏年の対応ができないわけだ。
まぁそもそも紀元前に閏年というものは無かったんだが、この際それは置いといて。
46億年前の日付に「地球誕生」というスケジュールを登録してみたかったんだが、
予想以上にてこずっております。
