在PHP中,命名空间用来解决在编写类库或应用程序时创建可重用的代码(如类或函数)时碰到的两类问题:
- 用户编写的代码与PHP内部的类/函数/常量或第三方类/函数/常量之间的名字冲突。
- 为很长的标识符名称创建一个别名或简短的名称,提高源代码的可读性。
PHP 在 5.3.0 以后的版本开始支持命名空间。
<?php
namespace my\name;
class MyClass {}
function myfunction() {}
const MYCONST = 1;
$a = new MyClass; // 等价于 $a = new \my\name\MyClass;
命名空间通过关键字namespace 来声明。如果一个文件中包含命名空间,必须在其它所有代码之前声明命名空间。
同一个命名空间可以定义在多个文件中,即允许将同一个命名空间的内容分割存放在不同的文件中。
与目录和文件的关系很像,PHP 命名空间也允许使用层次化的命名空间的名称。因此,命名空间的名称可以使用分层次的方式定义,如:
namespace Admin\Business\UserBusiness;
也可以在同一个文件中定义多个命名空间。在实际编程中,不提倡在同一个文件中定义多个命名空间。这种方式主要用于将多个 PHP 脚本合并到同一个文件中。将全局的非命名空间中的代码与命名空间中的代码组合到一个文件中,只能使用大括号形式的语法。全局代码必须用一个不带名称的 namespace 语句加上大括号括起来。
魔术常量__NAMESPACE__
的值是包含当前命名空间名称的字符串。如果是全局的代码(不包括在任何命名空间中的代码),它是一个空的字符串。
PHP中的命名空间支持两种使用别名或导入的方式:为类名称使用别名,或为命名空间名称使用别名。注意PHP不支持导入函数或常量。
如果没有定义任何命名空间,所有的类、函数和常量的定义都是在全局空间。在名称前加上反斜杠前缀\,表示该名称是全局空间中的名称。
示例:
<?php
namespace A\B\C;
/* 这个函数是 A\B\C\fopen */
function fopen() { // 命名空间中自定义的fopen函数
/* ... */
$f = \fopen(...); // 调用全局的fopen函数(即PHP自身内置的fopen函数)
return $f;
}
?>
6. 名称解析规则
在命名空间中,当遇到一个非限定的类、函数或常量名称时,会使用不同的优先策略对名称进行解析:
- 类名称总是解析到当前命名空间中的名称。因此在访问系统内部或不包含在命名空间中的类名称时,必须使用完全限定名称。
- 对于函数和常量来说,如果当前命名空间中不存在该函数或常量,会退而使用全局空间中的函数或常量。