ホームページ >バックエンド開発 >PHPチュートリアル >PHP名前空間の使い方を詳しく解説(Namespace)_PHPチュートリアル

PHP名前空間の使い方を詳しく解説(Namespace)_PHPチュートリアル

WBOY
WBOYオリジナル
2016-07-21 15:10:37799ブラウズ

名前空間については、公式ドキュメントで詳しく説明されています[表示]。ここでいくつかの練習と要約を行いました。

名前空間の最も明確な目的の 1 つは、重複した名前の問題を解決することです。PHP では、2 つの関数またはクラスが同じ名前を持つことを許可しません。そうしないと、致命的なエラーが発生します。この場合、名前の重複を避ける限り解決できます。最も一般的な方法は、プレフィックスを合意することです。

例: プロジェクトには記事とメッセージボードの 2 つのモジュールがあり、それぞれにユーザー メッセージを処理するためのクラス Comment があります。後で、すべてのユーザー メッセージの情報統計関数を追加する場合があります。たとえば、すべてのメッセージの数を取得したいとします。この時点で、Comment によって提供されるメソッドを呼び出すことは良い考えですが、それぞれの Comment クラスを同時に導入することは明らかに不可能であり、コードでエラーが発生し、Comment を別の場所に書き換えるとエラーが発生します。メンテナンス性が低下します。現時点では、次のようにクラス名の前にモジュール名を追加して、クラス名を再構築することしかできません。

ご覧のとおり、名前が非常に長くなりました。これは、将来コメントを使用するときに、より多くのコード (少なくともより多くの文字) が記述されることを意味します。さらに、将来的に各モジュールに統合関数を追加したり、相互に呼び出したりする場合は、名前が重複した場合に名前を再構築する必要があります。もちろん、プロジェクトの開始時にこの問題に気づき、名前付けルールを指定することで、この問題は回避できます。別の解決策は、名前空間を使用することです。


注:

この記事で言及されている定数: PHP5.3 以降、const キーワードはクラスの外で使用できるようになりました。 const と define はどちらも定数の宣言に使用されます (その違いについては詳しく説明しません) が、名前空間では、define はグローバルに機能するのに対し、const は現在の空間に対して機能します。記事内で言及した定数は、const を使用して宣言された定数を指します。


基本
名前空間は、コードを異なる空間(領域)に分割します。 各空間内の定数、関数、クラスの名前(面倒なので、以下では要素と呼びます)は互いに影響しません。同様に、私たちはよく「カプセル化」という概念を参照します。

名前空間を作成するには、次のように namespace キーワードを使用する必要があります:

コードをコピーします コードは次のとおりです:

//「Article」という名前の名前空間を作成します

namespace Article;

?>


現在のスクリプト ファイルの最初の名前空間の前にコードを置くことはできないことに注意してください。次の記述は間違っています:

コードをコピーします コードは次のとおりです。
/ /例 1
//スクリプトの前にロジック コードを書きます

$path = "/";

クラスコメント{ }

名前空間の記事;

?>

//例 2

//一部の文字がスクリプトの前に出力されます

名前空間の記事;

?>


なぜ最初の名前空間を言いたいのですか?同じスクリプト ファイル内に複数の名前空間を作成できるためです。
以下の 2 つの名前空間を作成し、これら 2 つの空間のそれぞれに Comment クラス要素を追加しました:


コードをコピーします コードは次のとおりです:

//「Article」という名前の名前空間を作成します

namespace Article;

//このコメントは記事スペースの要素に属します

クラス Comment { }

//「MessageBoard」という名前の名前空間を作成します
namespace MessageBoard;

//このコメントは MessageBoard スペースの要素に属します

Comment { }
?>

異なるスペース間で他の要素を直接呼び出すことはできません。 名前空間構文を使用する必要があります:

コードをコピーします。 コードは次のとおりです:

名前空間の記事;

クラスコメント{ }

名前空間メッセージボード;


クラスコメント{ }

//現在のスペース(MessageBoard)のCommentクラスを呼び出します

$comment = new Comment();


//Article スペースの Comment クラスを呼び出します

$article_comment = new ArticleComment();


?>


メッセージボードスペースの記事スペースでCommentクラスを呼び出す際に、ファイルパスのような構文が使用されていることがわかります: スペース名 要素名
クラスを除き、関数と定数の使い方は同じです。以下では、2つのスペースに新しい要素を作成し、その値をメッセージボードスペースに出力します。


コードをコピーします コードは次のとおりです:

名前空間の記事;

const PATH = '/article';

関数 getCommentTotal() {
100 を返す;
}

クラスコメント{ }


名前空間メッセージボード;

const PATH = '/message_board';

関数 getCommentTotal() {
300 を返す;
}

クラスコメント{ }

//現在のスペースで定数、関数、クラスを呼び出します
echo PATH; ///message_board
echo getCommentTotal() //300
$comment = new Comment();

//記事空間の定数、関数、クラスを呼び出す
echo ArticlePATH; ///article
echo ArticlegetCommentTotal() //100
$article_comment = new ArticleComment();

;

?>


これで、Article スペースの要素データを取得できました。


サブスペース
ネームスペースの呼び出し構文はファイル パスに似ており、これによりサブスペースをカスタマイズして各空間間の関係を記述することができます。

申し訳ありませんが、2 つのモジュールの記事と掲示板が実際には同じブログ プロジェクト内にあることを忘れていました。名前空間を使用してそれらの関係を表現すると、次のようになります:

コードをコピーします コードは次のとおりです:

//この名前空間を使用して blog の下の記事モジュールを表します
namespace BlogArticle;

クラスコメント{ }


//この名前空間を使用して、ブログ
名前空間 BlogMessageBoard;

の下のメッセージ ボード モジュールを表します。

クラスコメント{ }

//現在のスペースのクラスを呼び出します
$comment = new Comment();

//BlogArticle スペースのクラスを呼び出します
$article_comment = new BlogArticleComment();

?>


さらに、部分空間は BlogArticleArchivesDate などの多くのレベルを定義することもできます


パブリックスペース
いくつかの便利な関数とクラスを含む common_inc.php スクリプトファイルがあります:

コードをコピーします コードは次のとおりです:

関数 getIP() { }

クラス FilterXSS { }

?>


このスクリプトを名前空間に導入すると、スクリプト内の要素はこの名前空間に属しなくなります。このスクリプトで他の名前空間が定義されていない場合、その要素は常にパブリック空間にあります:
コードをコピーします コードは次のとおりです:

名前空間ブログ記事;

//スクリプトファイルを導入します
include './common_inc.php';

$filter_XSS = new FilterXSS(); //致命的なエラー: BlogArticleFilterXSS クラスが見つかりません

$filter_XSS = 新しい FilterXSS() //修正します

;

?>


パブリック スペースを呼び出す方法は、要素名の前に直接追加することです。そうしないと、PHP パーサーは現在のスペース内の要素を呼び出したいと認識します。カスタム要素に加えて、PHP 独自の要素も含まれており、それらはすべてパブリック スペースに属します。

実際には、パブリックスペースの関数と定数は追加しなくても通常どおり呼び出すことができることに言及したいと思います(なぜPHPがこれを行うのか理解できません)が、要素を正しく区別するために、呼び出すときに

を追加することをお勧めします。機能。


名前の用語
エイリアスとインポートについて話す前に、スペースの 3 つの名前の用語と、PHP がそれらを解析する方法について知っておく必要があります。公式ドキュメントは非常に優れているので、そのまま使用しました。

1. 修飾されていない名前、またはプレフィックスのないクラス名 ($comment = new Comment(); など)。現在の名前空間が BlogArticle の場合、Comment は BlogArticleComment として解析されます。コメントを使用するコードに名前空間 (グローバル空間) のコードが含まれていない場合、コメントはコメントとして解析されます。

2. 修飾名、またはプレフィックスを含む名前 ($comment = new ArticleComment(); など)。現在の名前空間が Blog の場合、Comment は BlogArticleComment として解析されます。コメントを使用するコードに名前空間 (グローバル空間) のコードが含まれていない場合、コメントはコメントとして解析されます。

3. 完全修飾名、または $comment = new ArticleComment(); などのグローバル接頭辞演算子を含む名前。この場合、Comment はコード内で常にリテラル名 ArticleComment に解決されます。

実際、これら 3 つの名前は、ファイル名 (comment.php など)、相対パス名 (./article/comment.php など)、絶対パス名 (/blog/article/comment など) と比較できます。 php)なので、より理解しやすくなる可能性があります。

それらを表すためにいくつかの例を使用しました:

コードをコピーします コードは次のとおりです:

//スペース ブログを作成する
名前空間ブログ;

クラスコメント{ }

//現在のブログ スペースを示す非修飾名
//この呼び出しは BlogComment();
$blog_comment = new Comment();

に解析されます

//ブログスペースに関連することを示す修飾名
//この呼び出しは BlogArticleComment();
$article_comment = new ArticleComment(); //クラスの前にバックスラッシュはありません

//ブログスペースへの絶対を示す完全修飾名
//この呼び出しは BlogComment();
$article_comment = new BlogComment(); //クラスの前にバックスラッシュがあります

//ブログスペースへの絶対を示す完全修飾名
//この呼び出しは BlogArticleComment();
$article_comment = new BlogArticleComment(); //クラスの前にバックスラッシュがあります

;


//ブログの部分空間記事を作成
namespace BlogArticle;

クラスコメント{ }

?>


実はこれまで非修飾名と完全修飾名を使ってきましたが、ようやく名前で呼べるようになりました。


エイリアスとインポート
エイリアスとインポートは、名前空間要素を呼び出すためのショートカットと考えることができます。 PHP は関数や定数のインポートをサポートしていません。

これらはすべて use 演算子を使用して実装されます:

コードをコピーします コードは次のとおりです:

名前空間ブログ記事;

クラスコメント{ }


//BBS スペースを作成します (フォーラムを開く予定です)
namespace BBS;

//名前空間をインポートします
use BlogArticle;
//名前空間をインポートした後、修飾名を使用して要素を呼び出すことができます
$article_comment = new ArticleComment();

//ネームスペースにエイリアスを使用する
use BlogArticle as Arte;
//スペース名の代わりにエイリアスを使用する
$article_comment = new ArteComment();

//クラスをインポートする
use BlogArticleComment;
//クラスをインポートした後、非修飾名を使用して要素を呼び出すことができます
$article_comment = new Comment();

//クラスにエイリアスを使用する
use BlogArticleComment as Comt;
//スペース名の代わりにエイリアスを使用する
$article_comment = new Comt();

?>


要素をインポートするときに、現在のスペースに同じ名前の要素がある場合はどうなるかに気付きました。明らかに、結果は致命的なエラーになります。

例:

コードをコピー コードは次のとおりです:

名前空間ブログ記事;

クラスコメント{ }


名前空間BBS;

クラスコメント{ }

クラス Comt { }


//クラスをインポートします
use BlogArticleComment;
$article_comment = new Comment(); //現在のスペースのコメントと競合し、プログラムは致命的なエラーを生成します

//クラスのエイリアスを使用する
use BlogArticleComment as Comt;
$article_comment = new Comt(); //現在のスペースの Comt と競合し、プログラムは致命的なエラーを生成します

?>


動的呼び出し
PHP は、動的アクセス要素の名前空間キーワードと __NAMESPACE__ マジック定数を提供します。 __NAMESPACE__ には、文字列を組み合わせることで動的にアクセスできます:
コードをコピーします コードは次のとおりです。

名前空間ブログ記事;

const PATH = '/ブログ/記事';

クラスコメント{ }

//namespace キーワードは現在のスペースを表します

echo namespacePATH; ///Blog/article
$comment = new namespaceComment();

//マジック定数 __NAMESPACE__ の値は現在のスペース名です

echo __NAMESPACE__; //BlogArticle

// を文字列に結合して
$comment_class_name = 'Comment';
$comment = new $comment_class_name と呼びます。 ();

?>


文字列形式での呼び出しの問題

上記の動的呼び出しの例では、文字列形式での動的呼び出しメソッドを示しましたが、このメソッドを使用する場合は、2 つの点に注意する必要があります。問題。

1. 二重引用符を使用すると特殊文字がエスケープされる場合があります


コードをコピーします コードは次のとおりです:

名前空間ブログ記事;

クラス名 { }

//BlogArticlename

$class_name = __NAMESPACE__ . //ただし、n は改行文字としてエスケープされます

;
$name = new $class_name() //致命的なエラーが発生しました

?>


2. 制限された名前とはみなされません

PHP は、スクリプトのコンパイル時に要素が配置されるスペースとインポート ステータスを決定します。スクリプトを解析するとき、文字列形式の呼び出しは非修飾名と完全修飾名のみとみなされ、修飾名であることはできません。

コードをコピーします コードは次のとおりです:

名前空間ブログ;

//Common クラスをインポートします
use BlogArticleCommon;
//非修飾名を使用して BlogArticleCommon を呼び出したいです
$common_class_name = 'Common';
//実際には非修飾名とみなされます。これは、しかし、現在のクラスは共通クラスを作成しませんでした
$common = new $common_class_name(); //致命的なエラーが発生しました: 共通クラスが存在しません

//修飾名を使用して BlogArticleCommon を呼び出したいです
$common_class_name = 'ArticleCommon';
//これは実際には完全修飾名とみなされ、これは Article スペースの下の Common クラスを意味しますが、定義するのは BlogArticle だけですArticle スペースの代わりに下のスペース
$common = new $common_class_name() //致命的なエラーが発生しました: ArticleCommon クラスが存在しません

;


名前空間ブログ記事;

クラス共通{ }

?>

概要
私は PHP 名前空間に触れたばかりなので、実践されていない提案をいくつかすることはできません。個人的には、プラグインや一般的なライブラリを作成する場合、名前空間の役割と機能は非常に強力だと思います。名前の重複を心配する必要はなくなりました。ただし、ある程度プロジェクトが進み、名前空間の追加などで名前の重複問題を解決する必要が出てきたら、名前のリファクタリング以上の作業量になると思います。その構文によってプロジェクトがある程度複雑になることは認めざるを得ません。そのため、プロジェクトの開始時から綿密に計画し、命名規則を策定する必要があります。

www.bkjia.comtru​​ehttp://www.bkjia.com/PHPjc/327051.html技術記事名前空間については、すでに公式ドキュメントで詳しく説明されています [表示] ので、ここでいくつかの練習と要約を行いました。 名前空間の最も明確な目的の 1 つは、PHP では許可されていない重複名の問題を解決することです...
声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。