somemo's diary

プログラマ、雑記、プログラミング関係はLinkから、数式はこっちでまとめていることが多い

【php】名前空間

名前空間を使用するソースをよく見るようになったので、気をつけておかなければならないことをまとめておきます。

名前空間

英語ではnamespaceと呼ばれています。名前のバッティングを防ぐための空間・領域という覚え方が一番しっくり来ると思います。5.3以前のクラス名は、PEARやZendのようなディレクトリをアンダースコアで表現したものや、symfony1系のようにsfといったprefixをつけています。本質的には、末尾のクラス名であるが、同一の名前になることを防ぐためにそうしてきました。

名前空間に属するもの

以下の4つです。

  • クラスと
  • インターフェイス
  • 関数
  • 定数

たぶん使いませんが・・・関数や定数も属するということは、名前空間さえつけてしまえば、既存の関数や定数と同じ名前のものが使えます。

名前空間の定義

namespaceを用いて定義します。名前空間を細かく分けたい場合には、\で区切ります。気持ち悪くて敬遠していたけど、慣れなきゃいけないものですし、慣れたら関係ないですね!

定義の前後のコード

名前空間を定義する直前には、以下の2つしか書けません。

declareの使い道が分からない・・・。

複数の名前空間

1ファイルに名前空間を複数定義できるようです。複数書く場合には、以下の2とおりです。

namespace 名前空間;
/* 処理 */

namespace 名前空間2;
/* 処理2 */
namespace 名前空間  { /* 処理 */  }
namespace 名前空間2 { /* 処理2 */ }

複数であれば、{}で記載したほうが分かりやすいと思います。しかし、複数の名前空間に属するクラスなどができると混乱の元になると思うので、1ファイル1名前空間を心がけたほうがよいと思います。

上記の2つの書き方を組み合わせるとエラーが発生しました。

<?php
namespace colon;
namespace kakko {}
Fatal error: Cannot mix bracketed namespace declarations with unbracketed namespace declarations in C:\script.php on line 2

グローバル名前空間

名前空間を定義しなかった場合、グローバルなものとして扱われます。しかし、1ファイルグローバル名前空間・独自グローバルを作成する場合、定義の前後のコードに反します。そこで、グローバル名前空間に属するように明示的に各方法があります。

namespace 名前空間  { /* 処理 */  }
namespace { /* グローバル処理 */ }

名前空間内に属するものがない場合

ファイルの先頭で名前空間を定義している場合、名前空間に属するものがなかった場合の挙動がものによって違います。以下のとおりです。

  • 探すのをやめてしまう(エラー)
    • クラス
    • インターフェース
  • グローバル名前空間から探す
    • 関数
    • 定数

標準例外が見つからないという記事をよく見ましたが、これのせいだったんですね。グローバルなクラスを使用する際には、クラス名の先頭に\をつけてグローバルであることを示さなくてはいけません。

使用方法

useによるインポートと、asによるエイリアスを用いて名前空間に属するものを使用できるようにしています。

namespace test;

use a\b\c as alias,
    d\e\f; // d\e\f as f

これで大体は問題ないはずだと思います。