PHP V5.3 で導入されたネームスペースは、PHP クラス、定数、関数にコンテキストを提供して、同じ名前の要素が一意であるとみなせるようにする方法です。一意の名前は、2 つのクラスまたは関数が同じ名前を使用する場合に発生する名前の競合を回避します。これらの PHP クラスは現実世界の同じオブジェクトを表す場合がありますが、その動作はまったく異なります。ネームスペースにより、正しい PHP クラス、定数、または関数が確実に存在し、PHP クラスを使用したい人が正しいクラスを使用していることを確認できます。
コード内の名前空間は、現実世界のコンテキストのようなものです。現実世界の車のオブジェクトを表すクラスについて考えてみましょう。たとえば、インターネット経由で自動車を販売する会社が使用する <font face="NSimsun">Automobile</font>
クラスは、保険を販売する会社が使用する <font face="NSimsun">Automobile</font>
クラスとはまったく異なる動作をする可能性があります。
アプリケーション開発者は、他の人が作成したコンポーネントを使用することができます。あなたがすでに使用しているクラス名を他の人が決して使用しないという保証はありませんが、クラスの動作は大きく異なります。名前空間が登場する前、PHP 開発者は、<font face="NSimsun">My_Enterprise_Person</font>
や <font face="NSimsun">XML_Validator</font>
などのクラス名にコンテキストを組み込むことがよくありました。
リスト 1 は、名前空間にあるクラスを示しています。
<br/><?php<br/>namespace IBM;<br/>class Foo {<br/>...<br/>}<br/>?><br/> |
以下は、名前空間内のクラスを参照する方法を示す例です。
<br/><?php<br/>$foo = new \IBM\Foo();<br/>?><br/> |
すべてのクラスに名前空間を追加する前に、名前空間ポリシーを定義することをお勧めします。時間をかけてある程度名前空間を構築することは可能ですが、名前空間の編成を容易にし、後で必要になる可能性のある変更を減らすために、名前空間の共通構造を決定することが最善です。ネームスペースを正しく使用すると、コンテキストを提供するだけでなく、PHP コードを整理するためにも使用できます。
Java™ や C# などの他の言語では、長い間名前空間が使用されてきました。名前空間の命名規則を選択する際には、多くの開発者が馴染みがあり、理解しやすいため、これらの言語の命名規則に似た規則を使用します。ただし、Java 言語とは異なり、PHP の名前空間とクラスが配置されているディレクトリの間には接続がありません。クラス、関数、または定数に対して任意の名前空間を選択できます。 1 つのファイルに複数の名前空間を使用することもできます。同時に、PHP 名前空間は C# とは異なります。クラスの外で関数または定数に名前空間を使用できます。
トップレベルの名前空間
組織の名前空間を構築している場合は、組織名をトップレベル ドメインとして使用できます。通常、組織が異なる目的を果たす多数のアプリケーションを作成しない限り、組織の名前を使用してトップレベルの名前空間を作成するだけで、PHP コードにコンテキストを提供し、名前の競合を回避できます。
リスト 3 は、トップレベルの名前空間を宣言する方法を示す例です。
<br/><?php<br/>namespace IBM;<br/>...<br/>?><br/> |
|
<br/><?php<br/>namespace IBM\DeveloperWorks;<br/>...<br/>?><br/> |
反斜杠(<font face="NSimsun">\</font>
)将次级名称空间 “developerWorks” 与顶级名称空间 “IBM” 分开。
在声明次级名称空间时,您可以使用两个常见技巧,或同时使用它们。获取名称空间的常见地方是项目名或应用程序名;另一个地方是域名。
通过项目定义
如果您使用组织名作为顶级名称空间,并且想通过次级名称空间来进一步提供上下文,那么可以使用项目名或应用程序名作为次级名称空间。例如,如果您构建一个称为 Greeter 的新应用程序(用于获取用户的名称并问候他们),那么清单 5 中的名称空间将为称为 <font face="NSimsun">Prompt</font>
的类提供完整的上下文。
<br/><?php<br/>namespace IBM\Greeter;<br/>class Prompt {<br/>...<br/>}<br/>?><br/> |
由于 <font face="NSimsun">Prompt</font>
可能是多个应用程序或库的类名,所以为该名称空间添加组织名和项目名能够让这个 <font face="NSimsun">Prompt</font>
类与其他同名的类区分开来。
通过域定义
使用域名是另一种选择次级名称空间的常见方式,如 清单 6 所示。它也可以用于项目名之后,是否使用取决于您对可重用性的计划(见 “根据可重用性命名”)。
域 是对更大的问题域的一组分类。域的一个例子是在更大型的应用程序中处理帐户、客户和产品的 “Account”、“Customers” 或 “Products”。
<br/><?php<br/>namespace IBM\MyApp\Account;<br/>class Address {<br/>...<br/>}<br/>?><br/> |
|
根据可重用性命名
除了应用支持可重用性的模块概念之外,类和名称空间的命名方式也能够实现可重用性。有时不良的命名方式会损害可重用性,因为不佳的名称暗示着类仅能用于特定目的。同样,错误地应用名称空间可能会不必要地局限类的使用范围,让它们的重用变得困难。
在使用组织名的顶级名称空间中,应该保留 “Common”、“Core”、“Lib” 等可跨应用程序重用的名称空间。一个常见的例子是验证,其中针对整个企业的库存单位(SKU)、帐号或发票号的规则是一样的,从而获得合适的规则和长度。对于 Validator 类,类似清单 7 的名称空间是不错的选择。
<br/><?php<br/>namespace MyCompany\Common\Validation;<br/>class NotNullValidator {<br/>...<br/>}<br/>?><br/> |
在这里,组织名用作顶级域(“MyCompany”)。“Common” 名称空间用作项目。即使在编写这个类的同时也许正在编写一个特定的应用程序,该类一样可以在组织的任何项目中使用。最后,“Validation” 用作类的域。
|
使用别名
尽管名称空间能够帮助您组织类并避免命名约定,但其缺点是名称过长。幸运的是,PHP 支持使用别名,因此可以在代码中使用更短的别名。清单 8 提供了一个示例。
<br/><?php<br/>use MyCompany\Common\Validation as Validators;<br/>?><br/> |
|
命名约定
名称空间命名使用单词首字母大写或 PASCAL 命名约定,这与其他 PHP 约定一样,比如 PHP Extension 和 Application Repository (PEAR) 包命名和文件名。例如,清单 9 中的名称空间比 清单 10 中的名称空间要好。
<br/><?php<br/>namespace MyNamespace;<br/>?><br/> |
避免使用与其他 PHP 约定冲突的命名和大小写约定。
<br/><?php<br/>namespace mynamespace;<br/>...<br/>?><br/> |
结束语
PHP 中的名称空间能够用于组织代码、避免命名冲突以及为类、函数和常量提供上下文。在名称空间中使用模式或约定让代码更易于理解,并且更易于引用和使用。