第18回 スケジューラーを作ろう(8) - タイムスタンプ - - PHP基礎講座

PHP 中級 講座

Saity先生のPHP基礎講座

Lecutures on PHP

第18回 スケジューラーを作ろう(8) - タイムスタンプ - (その1)

 このエントリーをはてなブックマークに追加
  • さぁ、今日も元気に張り切って行きましょうか!
  • 先生、何かいいことでもあったんですか?saity
  • いやぁ、この前、僕の抱えてるプロジェクトがやっと一つ完了してね。やっている間は忙しくて大変だったけど、完成するとやっぱりうれしいもんだよ(しみじみ)。
  • ふ~ん、まだまだ私にはわからない世界だなぁ。。。
  • もっと上達して、自分でアプリケーションが作れるようになってくると、完成したときの喜びもどんどんわかってくるよ。
  • そっか~。今でも、PHPを学ぶのは楽しいですけどね☆その楽しさを味わうために、今は努力努力、ですね!
  • その通り。じゃあ、今回の講座もがんばって学んでいこうか!
  • はーい。

曜日と日付を紐付けよう

  • この前は、カレンダー作成のために月の最初の日と最後の日を取得する方法を学習したね。
  • うんうん。じゃぁ、あとはこれを表形式に直せばいいのね。
  • もちろんこのまま表にしてしまってもいいけど、せっかくのカレンダーなんだから曜日をつけるようにしよう。
  • 曜日ですかぁ。そういえば、date関数の引数の中にそんな項目があった気もするわ。
  • ぉ~、よく覚えてるねぇ。date関数の第1引数に"w"を指定すると、その日の曜日にあたる数字(日曜日から土曜日を0から6で表したもの)を返してくれるんだ。
  • ふむふむ。それを使って月の全日付の曜日を調べていけばいいんですね!えっと。。。こんな感じかな?
// 最初の日と最後の日の「日にち」の部分だけ数字で取り出す。
$first_day date("j"$first_date);
$last_day date("j"$last_date);

 
// 全ての日の曜日を得る。
for($day $first_day$day <= $last_day$day++) {
  
$week[$day] = date("w"$day);
}
  • date関数の"j"で、最初の日と最後の日の数字をとってきて、その間をfor文で1日ずつ増やしていってみました☆あとは、その日付をキーにした配列の値に、曜日を入れて。。。
  • なるほど、発想は悪くないね。 でも、これはとても大切なところが間違っているんだ。saity
  • えぇ~。どこですか?!
  • date("w", $day)のところだよ。date関数のマニュアルをきちんと参照するとわかるけど、第2引数に指定するべきなのは日付ではなく「タイムスタンプ」と呼ばれるコンピュータが日時を理解するための値なんだ。
  • そっかぁ、これじゃだめなんだ。じゃあ、どういう風に指定すればいいんですか?
  • ちょっと前回を思い出してみて欲しい。$first_dateと$last_dateは、mktime関数で作った日付だったよね。
$first_date mktime(000date("m"), 1date("Y"));
// 中略
print("今月の最初の日は" date("Y-m-d"$first_date) . "です。\n");
  • そうそう。これは「今月の最初の日」って指定したんですよね~。
  • うん。実は、このmktime関数が作っていたのは「今月の最初の日」を表す日付ではなくて、それを変換したタイムスタンプという特殊な数値だったんだ。

- Saity先生のワンポイント講座 -

タイムスタンプ

タイムスタンプのワンポイント

 文中では「特殊な数値」といったけど、実はタイムスタンプの正体は、[1970年1月1日 00:00:00]から、指定した時刻までの合計秒数なんだ。
もしコンピューターに西暦や年月日を使った日時を理解させようとすると、日時専用の特殊なデータ処理が必要になってしまって、少し面倒だよね。
そこで、そのような特殊な処理を行わなくても大丈夫な日時の表し方として、基準時刻からの経過秒数で表す「タイムスタンプ」というものが作られたんだ。
タイムスタンプは普通の数値と同じように扱うことが出来るので、コンピュータも特殊な処理をする必要が少なくて済むので、プログラム上での日時データのやり取りの際に良く使われるんだ。

  • ふむふむ。
  • だから、date関数の第2引数に単純に$dayを渡してもおかしな結果になってしまうんだよ。
  • そうかぁ~。ということは、きちんと曜日を出すためには、次のように書けばいいんですね!
// 最初の日と最後の日の「日にち」の部分だけ数字で取り出す。
$first_day date("j"$first_date);
$last_day date("j"$last_date);

 
// 全ての日の曜日を得る。
for($day $first_day$day <= $last_day$day++) {
  
$day_timestamp mktime(000date("m"), $daydate("Y"));
  
$week[$day] = date("w"$day_timestamp);
}
  • OK☆これで$weekの配列の値に曜日が入ってくるね。
  • ほっ。。。あとは、これをカレンダーの表の形に表示できれば完成かな☆

カレンダー表示をしよう

  • よし、それじゃあ後は一気にカレンダーの表示まで作ってしまおうか。schedule_calendar.phpとでも名前をつけておきましょ。
  • よぅし。。。(タタタタ)
schedule_calendar.php
<?php
$first_date 
mktime(000date("m"), 1date("Y"));
$last_date mktime(000date("m") + 10date("Y"));

// 最初の日と最後の日の「日にち」の部分だけ数字で取り出す。
$first_day date("j"$first_date);
$last_day date("j"$last_date);

// 全ての日の曜日を得る。
for($day $first_day$day <= $last_day$day++) {
  
$day_timestamp mktime(000date("m"), $daydate("Y"));
  
$week[$day] = date("w"$day_timestamp);
}

?>
<html>
<head>
<title>カレンダー</title>
</head>
<body>
<table border="1">
  <tr>
    <th>日</th>
    <th>月</th>
    <th>火</th>
    <th>水</th>
    <th>木</th>
    <th>金</th>
    <th>土</th>
  </tr>
  <tr>
    <?php
    
// カレンダーの最初の空白部分
    
for ($i 0$i $week[$first_day]; $i++) {
      print(
"<td></td>\n");
    }

    for (
$day $first_day$day <= $last_day$day++) {
      if (
$week[$day] == 0) {
        print(
"</tr>\n<tr>\n");
      }
      print(
"<td>$day</td>\n");
    }

     
// カレンダーの最後の空白部分
    
for ($i $week[$last_day] + 1$i 7$i++) {
      print(
"<td></td>\n");
    }
    
?>
  </tr>
</table>
</body>
</html>
  • おおー、すばらしい(ホレボレ)。saity
  • へへ~。日曜日だったらをはさんで、次の行に移ってから続けるようにしたんです。
  • うんうん。カレンダーの、日付が入らない空白部分もきちんと作れているね。
  • ふふふ(エヘン)。最初の空白部分は、$first_dayの曜日の前まで、最後の空白は$last_dayの曜日の次から、中身が空のをうめてみました☆
  • これでカレンダーが出来上がったから、あとはこれまでに作ったスケジューラーの各機能を組み合わせていこうか。
  • ぉぉ、そろそろ完成の予感。。。
  • 1
  • 2

  



Pick Up Q&A

Q
負荷時のmysql_connect()エラー
 このエントリーをはてなブックマークに追加 
A
これはPHPというよりOSまたはMySQLのコミュニティで質問されたほうがいいと思います。 ぱっと思いついた範囲で記すと MySQL等のDBに「ある時点において同時に接続可能なクライアントの最大数」に制限があるよう...

>>続きを読む

今回のような実践的な経験がエンジニアのキャリアに繋がると思います。是非サービスを成功させて下さい!

▲解説者:岡本(アシアル株式会社 教育コーディネーター兼 システムエンジニア)