PHP5でデザインパターン − Singletonパターン

久々に書いたつもりのエントリが残ってないと凹む。確認画面でサヨウナラ。
気を取り直して、今回は実装は簡単だけど気が利いて実用性も高いSingletonパターンです。
このパターンは、インスタンスを一つしか生成しないためのパターンです。DB接続などで使うと、不要な接続を行わずに済みます。

まずは、クラスの定義から。

MessageBox.class.php

<?php
/**
 * SingletonパターンによるMessageBox
 */

class MessageBox
{
    static $instance;
    private $_msg;

    private function __construct() {
        echo "create MessageBox<br>\n";
    }

    static function getInstance()
    {
        if (self::$instance === null) {
            self::$instance = new MessageBox();
        }
        return self::$instance;
    }

    public function setMsg($msg)
    {
        $this->_msg = $msg;
    }

    public function getMsg()
    {
        return $this->_msg;
    }
}

コンストラクタをprivateにすることで、外部からnewできなくなっています。インスタンスはstaticなメソッドgetInstanceを通して取得します。
次に、クライアントサイドのコード。

msgboxTest.php

<?php
/**
 * Singletonパターンのテスト
 */

require_once 'MessageBox.class.php';

$box1 = MessageBox::getInstance();
$box1->setMsg('hello');
echo "BOX1:".$box1->getMsg()."<br>\n";

$box2 = MessageBox::getInstance();
$box2->setMsg('bye');
echo "BOX2:".$box2->getMsg()."<br>\n";
echo "BOX1:".$box1->getMsg()."<br>\n";

if ($box1 === $box2) {
    echo '$box1 === $box2'."<br>\n";
}

$box3 = new MessageBox();

このコードの実行結果はこちら
$box2のsetMsgメソッドが$box1にも影響していることが分かります。また、=== による比較で同一のインスタンスであることも確認できました。
最後に、newでインスタンスを生成しようとしていますが、MessageBoxのコンストラクタはprivateなので外部から呼び出すことはできません。エラーで終了します。

Head Firstデザインパターン ―頭とからだで覚えるデザインパターンの基本

Head Firstデザインパターン ―頭とからだで覚えるデザインパターンの基本