namespace PHP (namespace)
PHP namespace (namespace) é adicionado no PHP 5.3, se você aprendeu C # e Java, namespace que não é nada de coisas novas. Mas em PHP que ainda tem um significado muito importante.
namespaces PHP pode resolver os dois problemas seguintes:
- código escrito pelo usuário dentro do PHP classes / funções / constantes ou conflitos de terceiros nome classes / funções / constantes entre.
- Como nomes de identificadores longos (geralmente para aliviar a primeira categoria definida) criar um alias (ou curta) o nome de melhorar a legibilidade do código-fonte.
definindo namespaces
Por padrão, todas as constantes, classes e nomes de função são colocados no espaço global, da mesma forma como antes do PHP suporte namespace.
declaração de namespace por namespace palavra-chave. Se um nome de arquivo contiver espaços, ele deve declarar o namespace antes de qualquer outro código. Sintaxe é como se segue;
< ?php // 定义代码在 'MyProject' 命名空间中 namespace MyProject; // ... 代码 ...
Você também pode definir diferentes namespaces no mesmo arquivo no código, tais como:
< ?php namespace MyProject1; // MyProject1 命名空间中的PHP代码 namespace MyProject2; // MyProject2 命名空间中的PHP代码 // 另一种语法 namespace MyProject3 { // MyProject3 命名空间中的PHP代码 } ?>
Antes de declarar um código legal único namespace é usada para definir o arquivo de origem métodos de codificação declarar comunicado. Todo o código não-PHP inclui espaços em branco não pode aparecer antes da declaração de namespace.
<?php declare(encoding='UTF-8'); //定义多个命名空间和不包含在命名空间中的代码 namespace MyProject { const CONNECT_OK = 1; class Connection { /* ... */ } function connect() { /* ... */ } } namespace { // 全局代码 session_start(); $a = MyProject\connect(); echo MyProject\Connection::start(); } ?>
O seguinte erro de sintaxe código irá ocorrer:
<html> <?php namespace MyProject; // 命名空间前出现了“<html>” 会致命错误 - 命名空间必须是程序脚本的第一条语句 ?>
subnamespaces
Relacionamento com diretórios e arquivos muito parecido, namespaces PHP também permite especificar o nome do espaço de nomes hierárquico. Assim, o nome do espaço de nomes pode ser definido usando uma maneira hierárquica:
<?php namespace MyProject\Sub\Level; //声明分层次的单个命名空间 const CONNECT_OK = 1; class Connection { /* ... */ } function Connect() { /* ... */ } ?>
O exemplo acima cria constante MyProject \ Sub \ Nível \ CONNECT_OK, tipo MyProject \ Sub \ Nível \ Connection e função MyProject \ Sub \ Nível \ Connect.
namespaces
PHP nome da classe namespace pode ser referenciado em três maneiras:
Nome não qualificado, ou o nome da classe não contém um prefixo, como $ a = new foo (); ou foo :: staticmethod ();. Se o namespace atual é currentnamespace, foo será interpretado como currentnamespace \ foo. Se foo é um código global, o código não contém qualquer namespace, será analisado como foo foo. Aviso: Se a função de namespace ou constante não está definido, em seguida, o nome da função ou nome da constante não qualificado vai ser resolvido para o nome da função global, ou nome constante.
nome qualificado, ou o nome contém o prefixo, como $ a = new subnamespace \ foo ( ); ou subnamespace \ foo :: staticmethod ();. Se o namespace atual é currentnamespace, em seguida, foo será analisado como currentnamespace \ subnamespace \ foo. Se foo é um código global, o código não contém qualquer namespace, foo será resolvido para subnamespace \ foo.
nome completo, ou incluir um nome global operador de prefixo, por exemplo, $ a = new \ currentnamespace \ foo (); ou \ currentnamespace \ foo :: staticmethod () ;. Neste caso, foo será sempre resolvido para o nome das palavras de código (literal nome) currentnamespace \ foo.
Aqui é um exemplo destas três maneiras:
código de arquivo file1.php
<?php namespace Foo\Bar\subnamespace; const FOO = 1; function foo() {} class foo { static function staticmethod() {} } ?>
código de arquivo file2.php
<?php namespace Foo\Bar; include 'file1.php'; const FOO = 2; function foo() {} class foo { static function staticmethod() {} } /* 非限定名称 */ foo(); // 解析为 Foo\Bar\foo resolves to function Foo\Bar\foo foo::staticmethod(); // 解析为类 Foo\Bar\foo的静态方法staticmethod。resolves to class Foo\Bar\foo, method staticmethod echo FOO; // resolves to constant Foo\Bar\FOO /* 限定名称 */ subnamespace\foo(); // 解析为函数 Foo\Bar\subnamespace\foo subnamespace\foo::staticmethod(); // 解析为类 Foo\Bar\subnamespace\foo, // 以及类的方法 staticmethod echo subnamespace\FOO; // 解析为常量 Foo\Bar\subnamespace\FOO /* 完全限定名称 */ \Foo\Bar\foo(); // 解析为函数 Foo\Bar\foo \Foo\Bar\foo::staticmethod(); // 解析为类 Foo\Bar\foo, 以及类的方法 staticmethod echo \Foo\Bar\FOO; // 解析为常量 Foo\Bar\FOO ?>
Note que para acessar qualquer classe, função global ou constante, você pode usar o nome totalmente qualificado, como \ strlen () ou \ Exception ou \ INI_ALL.
Namespace Acessando as classes globais, funções e constantes:
<?php namespace Foo; function strlen() {} const INI_ALL = 3; class Exception {} $a = \strlen('hi'); // 调用全局函数strlen $b = \INI_ALL; // 访问全局常量 INI_ALL $c = new \Exception('error'); // 实例化全局类 Exception ?>
Namespaces e recursos de linguagem dinâmica
Implementar PHP namespace afetados por suas próprias características de linguagem dinâmica. Então, se você quiser o seguinte código em namespaces, elementos de acesso dinâmico.
código de arquivo example1.php:
<?php class classname { function __construct() { echo __METHOD__,"\n"; } } function funcname() { echo __FUNCTION__,"\n"; } const constname = "global"; $a = 'classname'; $obj = new $a; // prints classname::__construct $b = 'funcname'; $b(); // prints funcname echo constant('constname'), "\n"; // prints global ?>
Você deve usar um nome totalmente qualificado (incluindo o nome da classe do namespace prefix). Observe que, como em um nome de dinâmica de classe, nome da função, ou nome constante, nome qualificado e o nome completo há diferença, então a barra invertida é desnecessário.
elemento namespace de acesso dinâmico
<?php namespace namespacename; class classname { function __construct() { echo __METHOD__,"\n"; } } function funcname() { echo __FUNCTION__,"\n"; } const constname = "namespaced"; include 'example1.php'; $a = 'classname'; $obj = new $a; // prints classname::__construct $b = 'funcname'; $b(); // prints funcname echo constant('constname'), "\n"; // prints global /* note that if using double quotes, "\\namespacename\\classname" must be used */ $a = '\namespacename\classname'; $obj = new $a; // prints namespacename\classname::__construct $a = 'namespacename\classname'; $obj = new $a; // also prints namespacename\classname::__construct $b = 'namespacename\funcname'; $b(); // prints namespacename\funcname $b = '\namespacename\funcname'; $b(); // also prints namespacename\funcname echo constant('\namespacename\constname'), "\n"; // prints namespaced echo constant('namespacename\constname'), "\n"; // also prints namespaced ?>
palavra-chave namespace e constantes __NAMESPACE__
PHP suporta duas maneiras de acessar os elementos de namespace atual Sumário interior, __ constantes NAMESPACE__ mágicas e palavra-chave namespace.
__NAMESPACE__ Valor constante é uma string contendo o nome do namespace atual. No global, o código não inclui qualquer namespace que contém uma cadeia vazia.
Exemplo __NAMESPACE__, num espaço de nomes de código
<?php namespace MyProject; echo '"', __NAMESPACE__, '"'; // 输出 "MyProject" ?>
__NAMESPACE__ Exemplo, o código mundial
<?php echo '"', __NAMESPACE__, '"'; // 输出 "" ?>
__NAMESPACE__ Constante criados dinamicamente, quando o nome é útil, por exemplo:
Use __NAMESPACE__ nome criado dinamicamente
<?php namespace MyProject; function get($classname) { $a = __NAMESPACE__ . '\\' . $classname; return new $a; } ?>
palavra-chave namespace pode ser usado para acessar explicitamente o namespace atual ou um elementos sub-namespace. É equivalente à classe de auto operador.
código de namespace operador de namespace
<?php namespace MyProject; use blah\blah as mine; // see "Using namespaces: importing/aliasing" blah\mine(); // calls function blah\blah\mine() namespace\blah\mine(); // calls function MyProject\blah\mine() namespace\func(); // calls function MyProject\func() namespace\sub\func(); // calls function MyProject\sub\func() namespace\cname::method(); // calls static method "method" of class MyProject\cname $a = new namespace\sub\cname(); // instantiates object of class MyProject\sub\cname $b = namespace\CONSTANT; // assigns value of constant MyProject\CONSTANT to $b ?>
operador de namespace, código global
<?php namespace\func(); // calls function func() namespace\sub\func(); // calls function sub\func() namespace\cname::method(); // calls static method "method" of class cname $a = new namespace\sub\cname(); // instantiates object of class sub\cname $b = namespace\CONSTANT; // assigns value of constant CONSTANT to $b ?>
Usando namespaces: Aliasing / Importação
namespaces PHP apoiar dois usando pseudônimos ou importar: Use um alias para o nome da classe, ou um alias para um nome de namespace. Note que o PHP não suporta a importação de uma função ou constante.
Em PHP, alias para uso do operador para alcançar o seguinte é um uso de todas as formas possíveis para importar três exemplos:
1, usando o operador de uso de importação / Alias
<?php namespace foo; use My\Full\Classname as Another; // 下面的例子与 use My\Full\NSname as NSname 相同 use My\Full\NSname; // 导入一个全局类 use \ArrayObject; $obj = new namespace\Another; // 实例化 foo\Another 对象 $obj = new Another; // 实例化 My\Full\Classname 对象 NSname\subns\func(); // 调用函数 My\Full\NSname\subns\func $a = new ArrayObject(array(1)); // 实例化 ArrayObject 对象 // 如果不使用 "use \ArrayObject" ,则实例化一个 foo\ArrayObject 对象 ?>
2, a linha que contém várias instruções de uso
<?php use My\Full\Classname as Another, My\Full\NSname; $obj = new Another; // 实例化 My\Full\Classname 对象 NSname\subns\func(); // 调用函数 My\Full\NSname\subns\func ?>
operação de importação é feita em tempo de compilação, mas um nome de classe dinâmica, nome da função, ou nome constante não é.
3, Importação e nome dinâmico
<?php use My\Full\Classname as Another, My\Full\NSname; $obj = new Another; // 实例化一个 My\Full\Classname 对象 $a = 'Another'; $obj = new $a; // 实际化一个 Another 对象 ?>
Além disso, a operação de importação afeta somente nomes não qualificados e qualificados. Totalmente nome qualificado porque ele é identificado, ele não é afetado pela importação.
4, importação e totalmente nomes qualificados
<?php use My\Full\Classname as Another, My\Full\NSname; $obj = new Another; // instantiates object of class My\Full\Classname $obj = new \Another; // instantiates object of class Another $obj = new Another\thing; // instantiates object of class My\Full\Classname\thing $obj = new \Another\thing; // instantiates object of class Another\thing ?>
Usando namespaces: alternativa de função global / constant
Em um espaço de nomes, quando o PHP encontra uma classe não qualificada, função ou nome de constante, ele usa um diferentes estratégias prioritárias para resolver o nome. O nome da classe do nome do atual namespace sempre resolve. Portanto, em um acesso interno ao sistema ou não incluído no namespace do nome da classe, você deve usar o nome totalmente qualificado, por exemplo:
1, acessar classes globais em um namespace
<?php namespace A\B\C; class Exception extends \Exception {} $a = new Exception('hi'); // $a 是类 A\B\C\Exception 的一个对象 $b = new \Exception('hi'); // $b 是类 Exception 的一个对象 $c = new ArrayObject; // 致命错误, 找不到 A\B\C\ArrayObject 类 ?>
Para as funções e constantes, a função não existir ou se as constantes namespace atual, o PHP irá cair de volta para funções ou constantes globais no espaço.
2, função global de espaço de nomes reservados / constantes
<?php namespace A\B\C; const E_ERROR = 45; function strlen($str) { return \strlen($str) - 1; } echo E_ERROR, "\n"; // 输出 "45" echo INI_ALL, "\n"; // 输出 "7" - 使用全局常量 INI_ALL echo strlen('hi'), "\n"; // 输出 "1" if (is_array('hi')) { // 输出 "is not array" echo "is array\n"; } else { echo "is not array\n"; } ?>
espaço global
Se você não definir qualquer namespace, todas as definições e funções de classe estão em um espaço global e PHP como antes da introdução do conceito de namespaces. Antes de o nome prefixado \ indica que o nome é um espaço de nome global, também é verdade de outro namespace, mesmo se o nome for localizado.
Descrição Use espaço global
<?php namespace A\B\C; /* 这个函数是 A\B\C\fopen */ function fopen() { /* ... */ $f = \fopen(...); // 调用全局的fopen函数 return $f; } ?>
namespace Order
Uma vez que com o espaço para nome, que é o uso mais propenso a erros de tempo de aula, para encontrar o caminho desta classe é o que o.
<?php namespace A; use B\D, C\E as F; // 函数调用 foo(); // 首先尝试调用定义在命名空间"A"中的函数foo() // 再尝试调用全局函数 "foo" \foo(); // 调用全局空间函数 "foo" my\foo(); // 调用定义在命名空间"A\my"中函数 "foo" F(); // 首先尝试调用定义在命名空间"A"中的函数 "F" // 再尝试调用全局函数 "F" // 类引用 new B(); // 创建命名空间 "A" 中定义的类 "B" 的一个对象 // 如果未找到,则尝试自动装载类 "A\B" new D(); // 使用导入规则,创建命名空间 "B" 中定义的类 "D" 的一个对象 // 如果未找到,则尝试自动装载类 "B\D" new F(); // 使用导入规则,创建命名空间 "C" 中定义的类 "E" 的一个对象 // 如果未找到,则尝试自动装载类 "C\E" new \B(); // 创建定义在全局空间中的类 "B" 的一个对象 // 如果未发现,则尝试自动装载类 "B" new \D(); // 创建定义在全局空间中的类 "D" 的一个对象 // 如果未发现,则尝试自动装载类 "D" new \F(); // 创建定义在全局空间中的类 "F" 的一个对象 // 如果未发现,则尝试自动装载类 "F" // 调用另一个命名空间中的静态方法或命名空间函数 B\foo(); // 调用命名空间 "A\B" 中函数 "foo" B::foo(); // 调用命名空间 "A" 中定义的类 "B" 的 "foo" 方法 // 如果未找到类 "A\B" ,则尝试自动装载类 "A\B" D::foo(); // 使用导入规则,调用命名空间 "B" 中定义的类 "D" 的 "foo" 方法 // 如果类 "B\D" 未找到,则尝试自动装载类 "B\D" \B\foo(); // 调用命名空间 "B" 中的函数 "foo" \B::foo(); // 调用全局空间中的类 "B" 的 "foo" 方法 // 如果类 "B" 未找到,则尝试自动装载类 "B" // 当前命名空间中的静态方法或函数 A\B::foo(); // 调用命名空间 "A\A" 中定义的类 "B" 的 "foo" 方法 // 如果类 "A\A\B" 未找到,则尝试自动装载类 "A\A\B" \A\B::foo(); // 调用命名空间 "A\B" 中定义的类 "B" 的 "foo" 方法 // 如果类 "A\B" 未找到,则尝试自动装载类 "A\B" ?>
Nome resolução Siga estas regras:
- Função nome totalmente qualificado da classe e as chamadas constantes resolvidos em tempo de compilação. Por exemplo nova \ A \ B resolve classe A \ B.
- Todos os nomes não qualificados e qualificados (não nomes totalmente qualificados) convertido em tempo de compilação com base em regras de importação actuais. Por exemplo, se o namespace A \ B \ C é importado como C, em seguida, uma chamada para C \ D \ e () será convertido em A \ B \ C \ D \ e ().
- Namespace dentro, todos os nomes qualificados não traduzidos de acordo com as regras de importação será adicionado ao nome do atual namespace na frente dele. Por exemplo, no namespace A \ B Interno chamada C \ D \ e (), então C \ D \ e () é traduzido para A \ B \ C \ D \ e ().
- nome da classe não-qualificado do conversor (com o nome completo em vez do nome de uma breve introdução) em tempo de compilação com base em regras de importação actuais. Por exemplo, se o namespace A \ B \ C é importado como C, o novo C () são convertidos para o novo A \ B \ C () .
- Namespace interno (como A \ B), chamadas para nome de função não qualificada é resolvido em tempo de execução. Por exemplo, uma chamada para a função foo () é resolvido como este:
- Procurar chamado A \ B \ foo no namespace atual () função
- Tente encontrar e chamar o global (global) função espaço foo ().
- Namespace (por exemplo, A \ B) interna para nome não qualificado ou qualificada dos nomes de classe (não nomes totalmente qualificados) chamada é resolvida em tempo de execução. Aqui está a chamada para new C () eo novo D \ E () do processo de resolução: new () parsing C:
- Encontre A \ B class \ C no namespace atual.
- Ele tenta fazer autoload A \ B \ C.
- Em nome da classe precedido pelo nome do namespace atual torna-se: A \ B \ D \ E , em seguida, olhar para a classe.
- Ele tenta fazer autoload A \ B \ D \ E.