1
0
mirror of https://github.com/php/doc-es.git synced 2026-03-23 23:12:09 +01:00
Files
archived-doc-es/language/namespaces.xml
2025-11-30 23:23:40 +01:00

1599 lines
52 KiB
XML

<?xml version="1.0" encoding="utf-8"?>
<!-- EN-Revision: 1651836ff309efd14a795eff44ee51455f66c7d3 Maintainer: PhilDaiguille Status: ready -->
<!-- Reviewed: no -->
<!-- CREDITS: DAnnebicque -->
<chapter xml:id="language.namespaces" xmlns="http://docbook.org/ns/docbook"
version="1.1">
<title>Los espacios de nombres</title>
<sect1 xml:id="language.namespaces.rationale">
<title>Introducción a los espacios de nombres</title>
<titleabbrev>Introducción</titleabbrev>
<?phpdoc print-version-for="namespaces"?>
<simpara>
¿Qué son los espacios de nombres? En su definición más amplia, representan
un medio para encapsular elementos. Esto puede concebirse como un concepto
abstracto, por varias razones. Por ejemplo, en un sistema de archivos, los
directorios representan un grupo de archivos asociados y sirven como espacio de nombres
para los archivos que contienen. Un ejemplo concreto es que el archivo
<literal>foo.txt</literal> puede existir en ambos directorios
<literal>/home/greg</literal> y <literal>/home/other</literal>, pero que
las dos copias de <literal>foo.txt</literal> no pueden coexistir
en el mismo directorio. Además, para acceder al archivo <literal>foo.txt</literal>
desde fuera del directorio <literal>/home/greg</literal>, es necesario especificar
el nombre del directorio utilizando un separador de directorios, como
<literal>/home/greg/foo.txt</literal>. El mismo principio se aplica a los
espacios de nombres en el mundo de la programación.
</simpara>
<simpara>
En el mundo de PHP, los espacios de nombres están diseñados para resolver dos problemas
que enfrentan los autores de bibliotecas y aplicaciones al reutilizar elementos
como clases o bibliotecas de funciones:
</simpara>
<para>
<orderedlist>
<listitem>
<simpara>
Colisiones de nombres entre el código que se crea, las clases, funciones
o constantes internas de PHP, o las de bibliotecas de terceros.
</simpara>
</listitem>
<listitem>
<simpara>
La capacidad de crear alias o acortar nombres como Nombres_Extremadamente_Largos
para ayudar a resolver el primer problema y mejorar la legibilidad
del código.
</simpara>
</listitem>
</orderedlist>
</para>
<simpara>
Los espacios de nombres de PHP proporcionan un medio para agrupar clases, interfaces,
funciones o constantes. Aquí hay un ejemplo de sintaxis de los espacios de nombres de PHP:
</simpara>
<example>
<title>Ejemplo de sintaxis de espacios de nombres</title>
<titleabbrev>Espacios de nombres</titleabbrev>
<programlisting role="php">
<![CDATA[
<?php
namespace mon\nom; // Ver la sección "Definición de espacios de nombres"
class MaClasse {}
function mafonction() {}
const MACONSTANTE = 1;
$a = new MaClasse;
$c = new \mon\nom\MaClasse; // Ver la sección "Espacio global"
$a = strlen('bonjour'); // Ver "Uso de espacios de nombres: retorno al espacio global
$d = namespace\MACONSTANTE; // Ver "El operador namespace y la constante __NAMESPACE__
$d = __NAMESPACE__ . '\MACONSTANTE';
echo constant($d); // Ver "Espacios de nombres y características dinámicas"
?>
]]>
</programlisting>
</example>
<note>
<simpara>
Los nombres de espacios de nombres no son sensibles a mayúsculas/minúsculas.
</simpara>
</note>
<note>
<para>
Los espacios de nombres <literal>PHP</literal>, así como los nombres compuestos
que comienzan con estos nombres (como <literal>PHP\Classes</literal>)
están reservados para el uso interno del lenguaje y no deben usarse
en el código del espacio de usuario.
</para>
</note>
</sect1>
<sect1 xml:id="language.namespaces.definition">
<title>Definición de espacios de nombres</title>
<?phpdoc print-version-for="namespaces"?>
<para>
Aunque el código PHP válido puede contenerse en un espacio de nombres,
solo los siguientes tipos de código pueden verse afectados por los espacios de nombres:
las clases (incluyendo las abstractas, los traits y los enums), las interfaces,
las funciones y las constantes.
</para>
<para>
Los espacios de nombres se declaran con la palabra clave <literal>namespace</literal>.
Un archivo que contiene un espacio de nombres debe declarar el espacio al principio
del archivo, antes de cualquier otro código, con una sola excepción: la palabra
clave <xref linkend="control-structures.declare" />.
<example>
<title>Declaración de un espacio de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
namespace MonProjet;
const CONNEXION_OK = 1;
class Connexion { /* ... */ }
function connecte() { /* ... */ }
?>
]]>
</programlisting>
</example>
<note>
<simpara>
Los nombres completamente calificados (es decir, los nombres que comienzan con un backslash)
no están autorizados en las declaraciones de espacios de nombres, ya que tales
construcciones se interpretan como expresiones de espacio de nombres relativo.
</simpara>
</note>
El único elemento autorizado antes de la declaración de espacio de nombres es la instrucción
<literal>declare</literal>, para definir la codificación del archivo fuente. Además,
ningún código no-PHP puede preceder a la declaración de espacio de nombres, incluyendo
espacios:
<example>
<title>Error de declaración de un espacio de nombres</title>
<programlisting role="php">
<![CDATA[
<html>
<?php
namespace MonProjet; // error fatal: el espacio de nombres debe ser el primer elemento del script
?>
]]>
</programlisting>
</example>
</para>
<para>
Además, a diferencia de otras estructuras de PHP, el mismo espacio de nombres puede
definirse en varios archivos, lo que permite dividir el contenido de un
espacio de nombres en varios archivos.
</para>
</sect1>
<sect1 xml:id="language.namespaces.nested">
<title>Declaración de un subespacio de nombres</title>
<titleabbrev>Subespacio de nombres</titleabbrev>
<?phpdoc print-version-for="namespaces"?>
<para>
Al igual que con los archivos y los directorios, los espacios de nombres también
son capaces de especificar una jerarquía de espacios de nombres. Por lo tanto,
un nombre de espacio de nombres puede definirse con sus subniveles:
<example>
<title>Declaración de un espacio de nombres con jerarquía</title>
<programlisting role="php">
<![CDATA[
<?php
namespace MonProjet\Sous\Niveau;
const CONNEXION_OK = 1;
class Connexion { /* ... */ }
function connecte() { /* ... */ }
?>
]]>
</programlisting>
</example>
En el ejemplo anterior, se crean la constante <literal>MonProjet\Sous\Niveau\CONNEXION_OK</literal>,
la clase <literal>MonProjet\Sous\Niveau\Connexion</literal> y la función
<literal>MonProjet\Sous\Niveau\connecte</literal>.
</para>
</sect1>
<sect1 xml:id="language.namespaces.definitionmultiple">
<title>Definición de varios espacios de nombres en el mismo archivo</title>
<titleabbrev>Definición de varios espacios de nombres en el mismo archivo</titleabbrev>
<?phpdoc print-version-for="namespaces"?>
<para>
También pueden declararse varios espacios de nombres en el mismo archivo.
Hay dos sintaxis autorizadas.
</para>
<para>
<example>
<title>Declaración de varios espacios de nombres, sintaxis de combinación simple</title>
<programlisting role="php">
<![CDATA[
<?php
namespace MonProjet;
const CONNEXION_OK = 1;
class Connexion { /* ... */ }
function connecte() { /* ... */ }
namespace AutreProjet;
const CONNEXION_OK = 1;
class Connexion { /* ... */ }
function connecte() { /* ... */ }
?>
]]>
</programlisting>
</example>
</para>
<para>
Esta sintaxis no se recomienda para combinar espacios de nombres
en un solo archivo. En su lugar, se recomienda utilizar
la sintaxis de llaves.
</para>
<para>
<example>
<title>Declaración de varios espacios de nombres, sintaxis de llaves</title>
<programlisting role="php">
<![CDATA[
<?php
namespace MonProjet {
const CONNEXION_OK = 1;
class Connexion { /* ... */ }
function connecte() { /* ... */ }
}
namespace AutreProjet {
const CONNEXION_OK = 1;
class Connexion { /* ... */ }
function connecte() { /* ... */ }
}
?>
]]>
</programlisting>
</example>
</para>
<para>
Se recomienda encarecidamente, como práctica de codificación, no mezclar
varios espacios de nombres en el mismo archivo. El uso recomendado es combinar
varios scripts PHP en el mismo archivo.
</para>
<para>
Para combinar varios códigos sin espacios de nombres en código con espacio de nombres,
solo se admite la sintaxis de llaves. El código global debe estar encerrado por un
espacio de nombres sin nombre, como este:
<example>
<title>Declaración de varios espacios de nombres con un espacio sin nombre</title>
<programlisting role="php">
<![CDATA[
<?php
namespace MonProjet {
const CONNEXION_OK = 1;
class Connexion { /* ... */ }
function connecte() { /* ... */ }
}
namespace { // código global
session_start();
$a = MonProjet\connecte();
echo MonProjet\Connexion::start();
}
?>
]]>
</programlisting>
</example>
</para>
<para>
No puede existir ningún código PHP fuera de las llaves del espacio de nombres,
excepto para abrir una nueva instrucción <literal>declare</literal>.
<example>
<title>Declaración de varios espacios de nombres con un espacio sin nombre (2)</title>
<programlisting role="php">
<![CDATA[
<?php
declare(encoding='UTF-8');
namespace MonProjet {
const CONNEXION_OK = 1;
class Connexion { /* ... */ }
function connecte() { /* ... */ }
}
namespace { // código global
session_start();
$a = MonProjet\connecte();
echo MonProjet\Connexion::start();
}
?>
]]>
</programlisting>
</example>
</para>
</sect1>
<sect1 xml:id="language.namespaces.basics">
<title>Uso de espacios de nombres: introducción</title>
<titleabbrev>Introducción</titleabbrev>
<?phpdoc print-version-for="namespaces"?>
<para>
Antes de discutir el uso de espacios de nombres, es importante comprender
cómo PHP deduce qué espacio de nombres está utilizando su código. Puede hacerse
una analogía simple entre los espacios de nombres de PHP y un sistema de archivos.
Hay tres formas de acceder a un archivo en un sistema de archivos:
<orderedlist>
<listitem>
<simpara>
Un nombre de archivo relativo, como <literal>foo.txt</literal>. Esto se resuelve
en <literal>dossiercourant/foo.txt</literal> donde <literal>dossiercourant</literal> es el
directorio de trabajo. Si el directorio actual es <literal>/home/foo</literal>,
este nombre se resuelve en <literal>/home/foo/foo.txt</literal>.
</simpara>
</listitem>
<listitem>
<simpara>
Una ruta relativa, como <literal>sub-dossier/foo.txt</literal>. Esto se
resuelve en <literal>dossiercourant/sub-dossier/foo.txt</literal>.
</simpara>
</listitem>
<listitem>
<simpara>
Una ruta absoluta, como <literal>/main/foo.txt</literal>. Esto se resuelve
en <literal>/main/foo.txt</literal>.
</simpara>
</listitem>
</orderedlist>
El mismo principio puede aplicarse a los espacios de nombres de PHP.
Por ejemplo, puede hacer referencia a una clase de tres maneras:
<orderedlist>
<listitem>
<simpara>
Un nombre sin calificador, o una clase sin prefijo, como
<literal>$a = new foo();</literal> o
<literal>foo::methodestatique();</literal>. Si el espacio de nombres actual
es <literal>espacedenomscourant</literal>, esto se resuelve en
<literal>espacedenomscourant\foo</literal>. Si el espacio de nombres es
global, es decir, el espacio de nombres sin nombre, esto se convierte en <literal>foo</literal>.
</simpara>
<simpara>
Una advertencia: los nombres sin calificador para funciones y constantes
se tomarán del espacio de nombres global, si la función
no está definida en el espacio de nombres actual. Ver
<link linkend="language.namespaces.fallback">Uso de espacios de nombres:
retorno al espacio de nombres global para funciones y constantes</link> para
más detalles.
</simpara>
</listitem>
<listitem>
<simpara>
Un nombre calificado, o una clase con prefijo como
<literal>$a = new sousespacedenoms\foo();</literal> o
<literal>sousespacedenoms\foo::methodestatique();</literal>. Si el espacio de nombres actual
es <literal>espacedenomscourant</literal>, esto se convierte
en <literal>espacedenomscourant\sousespacedenoms\foo</literal>. Si
el código es global, es decir, el espacio de nombres sin nombre,
esto se convierte en <literal>sousespacedenoms\foo</literal>.
</simpara>
</listitem>
<listitem>
<simpara>
Un nombre absoluto, o un nombre con prefijo con un operador global como
<literal>$a = new \espacedenomscourant\foo();</literal> o
<literal>\espacedenomscourant\foo::methodestatique();</literal>. Esto siempre
hace referencia al nombre literal especificado en el código: <literal>espacedenomscourant\foo</literal>.
</simpara>
</listitem>
</orderedlist>
</para>
<para>
Aquí hay un ejemplo de las tres sintaxis, en código real:
<informalexample>
<simpara>file1.php</simpara>
<programlisting role="php">
<![CDATA[
<?php
namespace Foo\Bar\sousespacedenoms;
const FOO = 1;
function foo() {}
class foo
{
static function methodestatique() {}
}
?>
]]>
</programlisting>
<simpara>file2.php</simpara>
<programlisting role="php">
<![CDATA[
<?php
namespace Foo\Bar;
include 'file1.php';
const FOO = 2;
function foo() {}
class foo
{
static function methodestatique() {}
}
/* nombre no calificado */
foo(); // Se convierte en Foo\Bar\foo
foo::methodestatique(); // Se convierte en Foo\Bar\foo, método methodestatique
echo FOO; // Se convierte en la constante Foo\Bar\FOO
/* nombre calificado */
sousespacedenoms\foo(); // Se convierte en la función Foo\Bar\sousespacedenoms\foo
sousespacedenoms\foo::methodestatique(); // se convierte en la clase Foo\Bar\sousespacedenoms\foo,
// método methodestatique
echo sousespacedenoms\FOO; // Se convierte en la constante Foo\Bar\sousespacedenoms\FOO
/* nombre absoluto */
\Foo\Bar\foo(); // Se convierte en la función Foo\Bar\foo
\Foo\Bar\foo::methodestatique(); // Se convierte en la clase Foo\Bar\foo, método methodestatique
echo \Foo\Bar\FOO; // Se convierte en la constante Foo\Bar\FOO
?>
]]>
</programlisting>
</informalexample>
</para>
<para>
Tenga en cuenta que para acceder a cualquier clase, función o constante
global, puede utilizarse un nombre absoluto, como
<function>\strlen</function> o <classname>\Exception</classname> o
\<constant>INI_ALL</constant>.
<example>
<title>Acceso a clases, funciones y constantes globales desde un espacio de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
namespace Foo;
function strlen() {}
const INI_ALL = 3;
class Exception {}
$a = \strlen('hi'); // llama a la función global strlen
$b = \INI_ALL; // acceso a una constante INI_ALL
$c = new \Exception('error'); // instancia la clase global Exception
?>
]]>
</programlisting>
</example>
</para>
</sect1>
<sect1 xml:id="language.namespaces.dynamic">
<title>Espacios de nombres y lenguaje dinámico</title>
<titleabbrev>Espacios de nombres y lenguaje dinámico</titleabbrev>
<?phpdoc print-version-for="namespaces"?>
<para>
La implementación de espacios de nombres de PHP está influenciada por su naturaleza
dinámica como lenguaje de programación. Por lo tanto, para convertir código como el
del siguiente ejemplo en un espacio de nombres:
<example>
<title>Acceso dinámico a elementos</title>
<simpara>example1.php:</simpara>
<programlisting role="php">
<![CDATA[
<?php
class classname
{
function __construct()
{
echo __METHOD__,"\n";
}
}
function funcname()
{
echo __FUNCTION__,"\n";
}
const constname = "global";
$a = 'classname';
$obj = new $a; // muestra classname::__construct
$b = 'funcname';
$b(); // muestra funcname
echo constant('constname'), "\n"; // muestra global
?>
]]>
</programlisting>
</example>
Es necesario utilizar un nombre absoluto (el nombre de la clase, con su prefijo de espacio de nombres).
Tenga en cuenta que no hay diferencia entre un nombre absoluto y un nombre calificado
en un nombre de clase, función o constante dinámica, lo que hace que el backslash
inicial no sea necesario.
<example>
<title>Acceso dinámico a espacios de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
namespace nomdelespacedenoms;
class classname
{
function __construct()
{
echo __METHOD__,"\n";
}
}
function funcname()
{
echo __FUNCTION__,"\n";
}
const constname = "namespaced";
/* Tenga en cuenta que si utiliza comillas dobles, "\\nomdelespacedenoms\\classname" debe usarse */
$a = '\nomdelespacedenoms\classname';
$obj = new $a; // muestra nomdelespacedenoms\classname::__construct
$a = 'nomdelespacedenoms\classname';
$obj = new $a; // también muestra nomdelespacedenoms\classname::__construct
$b = 'nomdelespacedenoms\funcname';
$b(); // muestra nomdelespacedenoms\funcname
$b = '\nomdelespacedenoms\funcname';
$b(); // también muestra nomdelespacedenoms\funcname
echo constant('\nomdelespacedenoms\constname'), "\n"; // muestra namespaced
echo constant('nomdelespacedenoms\constname'), "\n"; // también muestra namespaced
?>
]]>
</programlisting>
</example>
</para>
<para>
Se recomienda leer la <link linkend="language.namespaces.faq.quote">nota sobre la protección de espacios de nombres en cadenas</link>.
</para>
</sect1>
<sect1 xml:id="language.namespaces.nsconstants">
<title>El comando namespace y la constante __NAMESPACE__</title>
<titleabbrev>Comando namespace y __NAMESPACE__</titleabbrev>
<?phpdoc print-version-for="namespaces"?>
<para>
PHP admite dos medios para acceder de manera abstracta a los elementos
en el espacio de nombres actual, a saber, la constante mágica
<constant>__NAMESPACE__</constant> y el comando <literal>namespace</literal>.
</para>
<para>
El valor de <constant>__NAMESPACE__</constant> es una cadena que contiene el nombre
del espacio de nombres actual. En el espacio global, sin nombre, contiene
una cadena vacía.
<example>
<title>Ejemplo con __NAMESPACE__, en un código con espacio de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
namespace MonProjet;
echo '"', __NAMESPACE__, '"'; // muestra "MonProjet"
?>
]]>
</programlisting>
</example>
<example>
<title>Ejemplo con __NAMESPACE__, en un código con espacio de nombres global</title>
<programlisting role="php">
<![CDATA[
<?php
echo '"', __NAMESPACE__, '"'; // muestra ""
?>
]]>
</programlisting>
</example>
La constante <constant>__NAMESPACE__</constant> es útil para construir
dinámicamente nombres, como:
<example>
<title>Uso de __NAMESPACE__ para una construcción dinámica de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
namespace MonProjet;
function get($classname)
{
$a = __NAMESPACE__ . '\\' . $classname;
return new $a;
}
?>
]]>
</programlisting>
</example>
</para>
<para>
El comando <literal>namespace</literal> también puede usarse para
solicitar explícitamente un elemento del espacio de nombres actual, o de un
subespacio. Es el equivalente para los espacios de nombres del operador
<literal>self</literal> de las clases.
<example>
<title>El operador namespace, en un espacio de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
namespace MonProjet;
use blah\blah as mine; // Ver "Uso de espacios de nombres: alias e importación"
blah\mine(); // llama a la función MonProjet\blah\mine()
namespace\blah\mine(); // llama a la función MonProjet\blah\mine()
namespace\func(); // llama a la función MonProjet\func()
namespace\sub\func(); // llama a la función MonProjet\sub\func()
namespace\cname::method(); // llama al método estático "method" de la clase MonProjet\cname
$a = new namespace\sub\cname(); // instancia un objeto de la clase MonProjet\sub\cname
$b = namespace\CONSTANT; // asigna el valor de la constante MonProjet\CONSTANT a $b
?>
]]>
</programlisting>
</example>
<example>
<title>El operador namespace, en el espacio de nombres global</title>
<programlisting role="php">
<![CDATA[
<?php
namespace\func(); // llama a la función func()
namespace\sub\func(); // llama a la función sub\func()
namespace\cname::method(); // llama al método estático "method" de la clase cname
$a = new namespace\sub\cname(); // instancia un objeto de la clase sub\cname
$b = namespace\CONSTANT; // asigna el valor de la constante CONSTANT a $b
?>
]]>
</programlisting>
</example>
</para>
</sect1>
<sect1 xml:id="language.namespaces.importing">
<?phpdoc print-version-for="namespaces"?>
<title>Uso de espacios de nombres: importación y alias</title>
<titleabbrev>Importación y alias</titleabbrev>
<para>
La capacidad de hacer referencia a un nombre absoluto con un alias o importando
un espacio de nombres es estratégica. Es un beneficio similar a los enlaces
simbólicos en un sistema de archivos.
</para>
<para>
PHP puede crear alias(/importar) constantes, funciones, clases, interfaces,
traits, enumeraciones y espacios de nombres.
</para>
<para>
Un alias se crea con el operador <literal>use</literal>.
Aquí hay un ejemplo que presenta los cinco tipos de importación:
<example>
<title>Importación y alias con el operador use</title>
<programlisting role="php">
<![CDATA[
<?php
namespace foo;
use My\Full\Classname as Another;
// Esto es lo mismo que use My\Full\NSname as NSname
use My\Full\NSname;
// importación de una clase global
use ArrayObject;
// importación de una función
use function My\Full\functionName;
// alias de una función
use function My\Full\functionName as func;
// importación de una constante
use const My\Full\CONSTANT;
$obj = new namespace\Another; // instancia un objeto de la clase foo\Another
$obj = new Another; // instancia un objeto de la clase My\Full\Classname
NSname\subns\func(); // llama a la función My\Full\NSname\subns\func
$a = new ArrayObject(array(1)); // instancia un objeto de la clase ArrayObject
// Sin la instrucción "use ArrayObject" habríamos instanciado un objeto de la clase foo\ArrayObject
func(); // Llama a la función My\Full\functionName
echo CONSTANT; // muestra el valor de My\Full\CONSTANT
?>
]]>
</programlisting>
</example>
Tenga en cuenta que para los nombres con ruta (los nombres absolutos que contienen
separadores de espacios, como <literal>Foo\Bar</literal>, en comparación con
los nombres globales, como <literal>FooBar</literal>, que no los contienen),
el backslash inicial no es necesario y no se recomienda, ya que los nombres importados
deben ser absolutos y no se resuelven relativamente al espacio de nombres actual.
</para>
<para>
Además, PHP admite atajos prácticos, como las instrucciones use múltiples.
<example>
<title>Importación y alias múltiples con el operador use</title>
<programlisting role="php">
<![CDATA[
<?php
use My\Full\Classname as Another, My\Full\NSname;
$obj = new Another; // instancia un objeto de la clase My\Full\Classname
NSname\subns\func(); // llama a la función My\Full\NSname\subns\func
?>
]]>
</programlisting>
</example>
</para>
<para>
La importación se realiza durante la compilación, por lo que no afecta
a las clases, funciones y constantes dinámicas.
<example>
<title>Importación y nombres de espacios dinámicos</title>
<programlisting role="php">
<![CDATA[
<?php
use My\Full\Classname as Another, My\Full\NSname;
$obj = new Another; // instancia un objeto de la clase My\Full\Classname
$a = 'Another';
$obj = new $a; // instancia un objeto de la clase Another
?>
]]>
</programlisting>
</example>
</para>
<para>
Además, la importación solo afecta a los nombres sin calificación. Los nombres
absolutos siguen siendo absolutos y no se modifican por una importación.
<example>
<title>Importación y nombres de espacios absolutos</title>
<programlisting role="php">
<![CDATA[
<?php
use My\Full\Classname as Another, My\Full\NSname;
$obj = new Another; // instancia un objeto de la clase My\Full\Classname
$obj = new \Another; // instancia un objeto de la clase Another
$obj = new Another\untruc; // instancia un objeto de la clase My\Full\Classname\untruc
$obj = new \Another\untruc; // instancia un objeto de la clase Another\untruc
?>
]]>
</programlisting>
</example>
</para>
<sect2 xml:id="language.namespaces.importing.scope">
<title>Reglas de contexto para la importación</title>
<para>
La palabra clave <literal>use</literal> debe declararse en el contexto más
externo de un archivo (el contexto global) o en las declaraciones de espacio
de nombres. Esto se debe a que la importación se realiza durante la compilación
y no durante la ejecución, por lo que no se pueden apilar los contextos. El ejemplo
siguiente muestra usos incorrectos de la palabra clave <literal>use</literal>:
</para>
<para>
<example>
<title>Reglas de importación incorrectas</title>
<programlisting role="php">
<![CDATA[
<?php
namespace Languages;
function toGreenlandic
{
use Languages\Danish;
// ...
}
?>
]]>
</programlisting>
</example>
</para>
<note>
<para>
Las reglas de importación se basan en archivos, lo que significa que los archivos
incluidos no heredarán <emphasis>PAS</emphasis> las reglas de importación del archivo padre.
</para>
</note>
</sect2>
<sect2 xml:id="language.namespaces.importing.group">
<title>Declaración del grupo <literal>use</literal></title>
<para>
Las clases, funciones y constantes importadas desde
el mismo &namespace; pueden agruparse en una
sola instrucción &use.namespace;.
</para>
<informalexample>
<programlisting role="php">
<![CDATA[
<?php
use some\namespace\ClassA;
use some\namespace\ClassB;
use some\namespace\ClassC as C;
use function some\namespace\fn_a;
use function some\namespace\fn_b;
use function some\namespace\fn_c;
use const some\namespace\ConstA;
use const some\namespace\ConstB;
use const some\namespace\ConstC;
// es equivalente a la siguiente declaración de grupo use
use some\namespace\{ClassA, ClassB, ClassC as C};
use function some\namespace\{fn_a, fn_b, fn_c};
use const some\namespace\{ConstA, ConstB, ConstC};
]]>
</programlisting>
</informalexample>
</sect2>
</sect1>
<sect1 xml:id="language.namespaces.global">
<title>Espacio de nombres global</title>
<titleabbrev>Global</titleabbrev>
<?phpdoc print-version-for="namespaces"?>
<para>
Sin ninguna definición de espacio de nombres, todas las clases y las funciones
se colocan en el espacio de nombres global: como en PHP antes de que los espacios
de nombres fueran introducidos. Al prefijar un nombre con un backslash
<literal>\</literal>, se puede solicitar el uso del espacio de nombres
global, incluso en un contexto de espacio de nombres específico.
<example>
<title>Especificación de espacio de nombres global</title>
<programlisting role="php">
<![CDATA[
<?php
namespace A\B\C;
/* Esta función es A\B\C\fopen */
function fopen() {
/* ... */
$f = \fopen(...); // llamada a fopen global
return $f;
}
?>
]]>
</programlisting>
</example>
</para>
</sect1>
<sect1 xml:id="language.namespaces.fallback">
<title>Uso de espacios de nombres: retorno al espacio global para funciones y constantes</title>
<titleabbrev>Retorno al espacio global</titleabbrev>
<?phpdoc print-version-for="namespaces"?>
<para>
En un espacio de nombres, cuando PHP encuentra un nombre sin calificación,
ya sea una clase, una función o una constante, lo resuelve con diferentes
prioridades. Los nombres de clases siempre se resuelven con el espacio de nombres actual.
Para acceder a clases internas o a clases que no están en
un espacio de nombres, es necesario representarlas con su nombre absoluto, como:
<example>
<title>Acceso a clases globales desde un espacio de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
namespace A\B\C;
class Exception extends \Exception {}
$a = new Exception('hi'); // $a es un objeto de la clase A\B\C\Exception
$b = new \Exception('hi'); // $b es un objeto de la clase Exception
$c = new ArrayObject; // error fatal, clase A\B\C\ArrayObject no encontrada
?>
]]>
</programlisting>
</example>
</para>
<para>
Para las funciones y constantes, PHP las buscará en el espacio
global si no puede encontrarlas en el espacio de nombres actual.
<example>
<title>Acceso a funciones y constantes globales en un espacio de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
namespace A\B\C;
const E_ERROR = 45;
function strlen($str)
{
return \strlen($str) - 1;
}
echo E_ERROR, "\n"; // muestra "45"
echo INI_ALL, "\n"; // muestra "7": acceso al espacio de nombres global INI_ALL
echo strlen('hi'), "\n"; // muestra "1"
if (is_array('hi')) { // muestra "no es un array"
echo "es un array\n";
} else {
echo "no es un array\n";
}
?>
]]>
</programlisting>
</example>
</para>
</sect1>
<sect1 xml:id="language.namespaces.rules">
<title>Reglas de resolución de nombres</title>
<titleabbrev>Reglas de resolución de nombres</titleabbrev>
<?phpdoc print-version-for="namespaces"?>
<para>
En el contexto de las reglas de resolución, hay varias definiciones importantes:
<variablelist>
<title>Definiciones para espacios de nombres</title>
<varlistentry>
<term>nombre no calificado</term>
<listitem>
<para>
Esto es un identificador que no contiene un separador de espacio de nombres.
Por ejemplo: <literal>Foo</literal>
</para>
</listitem>
</varlistentry>
<varlistentry>
<term>nombre calificado</term>
<listitem>
<para>
Esto es un identificador que contiene un separador de espacio de nombres.
Por ejemplo: <literal>Foo\Bar</literal>
</para>
</listitem>
</varlistentry>
<varlistentry>
<term>Nombre absoluto</term>
<listitem>
<para>
Esto es un identificador que comienza con un separador de espacio de nombres.
Por ejemplo: <literal>\Foo\Bar</literal>. El espacio de nombres <literal>Foo</literal>
también es un nombre absoluto.
</para>
</listitem>
</varlistentry>
<varlistentry>
<term>Nombre Relativo</term>
<listitem>
<para>
Es un identificador que comienza con <literal>namespace</literal>, como
<literal>namespace\Foo\Bar</literal>.
</para>
</listitem>
</varlistentry>
</variablelist>
</para>
<para>
Los nombres se resuelven siguiendo las siguientes reglas:
<orderedlist>
<listitem>
<simpara>
Los nombres absolutos siempre se traducen a nombres sin el separador de namespace.
Por ejemplo, <literal>\A\B</literal> se traduce a <literal>A\B</literal>.
</simpara>
</listitem>
<listitem>
<simpara>
Todos los nombres que no son absolutos se traducen con
<literal>namespace</literal> reemplazado por el namespace actual.
Si el nombre aparece en el namespace global, el prefijo
<literal>namespace\</literal> se elimina. Por ejemplo <literal>namespace\A</literal>
en el namespace <literal>X\Y</literal> se traduce a <literal>X\Y\A</literal>.
El mismo nombre en el namespace global se traduce a <literal>A</literal>.
</simpara>
</listitem>
<listitem>
<simpara>
Para los nombres absolutos, el primer segmento se traduce
de acuerdo con la clase/namespace de la tabla de importación.
Por ejemplo, si el namespace <literal>A\B\C</literal> se importa como <literal>C</literal>, el nombre <literal>C\D\E</literal> se traduce a <literal>A\B\C\D\E</literal>.
</simpara>
</listitem>
<listitem>
<simpara>
Para los nombres absolutos, si ninguna regla de importación
se aplica, el namespace actual se prefiere al nombre.
Por ejemplo, el nombre <literal>C\D\E</literal> en el namespace <literal>A\B</literal>,
se traduce a <literal>A\B\C\D\E</literal>.
</simpara>
</listitem>
<listitem>
<simpara>
Para los nombres absolutos, el nombre se traduce en relación con la tabla actual de importación para el tipo de símbolo respectivo.
Esto significa que un nombre que se asemeja a una clase se traduce de acuerdo con la tabla de importación de
class/namespace, los nombres de funciones utilizando la
tabla de importación de funciones, y las constantes utilizando la tabla de importación de constantes.
Por ejemplo, después
<literal>use A\B\C;</literal> un uso como <literal>new C()</literal> corresponde al nombre
<literal>A\B\C()</literal>. De manera similar, después de <literal>use function A\B\foo;</literal> un uso
como <literal>foo()</literal> corresponde al nombre <literal>A\B\foo</literal>.
</simpara>
</listitem>
<listitem>
<simpara>
Para los nombres relativos, si ninguna regla se aplica, y el nombre
hace referencia a una clase, el namespace actual sirve como prefijo.
Por ejemplo <literal>new C()</literal> en el namespace
<literal>A\B</literal> corresponde al nombre <literal>A\B\C</literal>.
</simpara>
</listitem>
<listitem>
<simpara>
Para los nombres relativos, si ninguna regla se aplica, y el nombre
hace referencia a una función o constante, y el código está
fuera del namespace global, el nombre se resuelve durante la ejecución.
Supongamos que el código está en el namespace
<literal>A\B</literal>, aquí es cómo se resuelve una llamada a la función <literal>foo()</literal>:
</simpara>
<orderedlist>
<listitem>
<simpara>
Busca una función en el espacio de nombres actual:
<literal>A\B\foo()</literal>.
</simpara>
</listitem>
<listitem>
<simpara>
Intenta encontrar y llamar a la función <emphasis>global</emphasis>
<literal>foo()</literal>.
</simpara>
</listitem>
</orderedlist>
</listitem>
</orderedlist>
</para>
<example>
<title>Ejemplos de resolución de espacios de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
namespace A;
use B\D, C\E as F;
// llamadas de funciones
foo(); // intenta llamar a la función "foo" en el espacio de nombres "A"
// luego llama a la función global "foo"
\foo(); // llama a la función "foo" definida en el espacio de nombres global
my\foo(); // llama a la función "foo" definida en el espacio de nombres "A\my"
F(); // intenta llamar a la función "F" definida en el espacio "A"
// luego intenta llamar a la función global "F"
// referencias de clases
new B(); // crea un objeto de la clase "B" definida en el espacio de nombres "A"
// si no se encuentra, intenta el autocargado en la clase "A\B"
new D(); // crea un objeto de la clase "D" definida en el espacio de nombres "B"
// si no se encuentra, intenta el autocargado en la clase "B\D"
new F(); // crea un objeto de la clase "E" definida en el espacio de nombres "C"
// si no se encuentra, intenta el autocargado en la clase "C\E"
new \B(); // crea un objeto de la clase "B" definida en el espacio de nombres global
// si no se encuentra, intenta el autocargado en la clase "B"
new \D(); // crea un objeto de la clase "D" definida en el espacio de nombres global
// si no se encuentra, intenta el autocargado en la clase "D"
new \F(); // crea un objeto de la clase "F" definida en el espacio de nombres global
// si no se encuentra, intenta el autocargado en la clase "F"
// métodos estáticos y funciones de espacio de nombres de otro espacio
B\foo(); // llama a la función "foo" del espacio de nombres "A\B"
B::foo(); // llama al método "foo" de la clase "B" definida en el espacio de nombres "A"
// si la clase "A\B" no se encuentra, intenta el autocargado en la clase "A\B"
D::foo(); // llama al método "foo" de la clase "D" definida en el espacio de nombres "B"
// si la clase "B\D" no se encuentra, intenta el autocargado en la clase "B\D"
\B\foo(); // llama a la función "foo" del espacio de nombres "B"
\B::foo(); // llama al método "foo" de la clase "B" ubicada en el espacio de nombres global
// si la clase "B" no se encuentra, intenta el autocargado en la clase "B"
// métodos estáticos y funciones de espacio de nombres del espacio actual
A\B::foo(); // llama al método "foo" de la clase "B" del espacio de nombres "A\A"
// si la clase "A\A\B" no se encuentra, intenta el autocargado en la clase "A\A\B"
\A\B::foo(); // llama al método "foo" de la clase "B" del espacio de nombres "A"
// si la clase "A\B" no se encuentra, intenta el autocargado en la clase "A\B"
?>
]]>
</programlisting>
</example>
</sect1>
<sect1 xml:id="language.namespaces.faq">
<title>Preguntas frecuentes: lo que debe saber sobre espacios de nombres</title>
<titleabbrev>Preguntas frecuentes</titleabbrev>
<?phpdoc print-version-for="namespaces"?>
<para>
Esta FAQ se divide en dos secciones: las preguntas comunes,
y los puntos particulares de la implementación, que pueden ser
útiles para la comprensión global.
</para>
<para>
Primero, las preguntas comunes.
<orderedlist>
<listitem>
<simpara>
<link linkend="language.namespaces.faq.shouldicare">Si no utilizo espacios
de nombres, ¿debo preocuparme por ellos?</link>
</simpara>
</listitem>
<listitem>
<simpara>
<link linkend="language.namespaces.faq.globalclass">¿Cómo utilizar una clase
global o interna desde un espacio de nombres?</link>
</simpara>
</listitem>
<listitem>
<simpara>
<link linkend="language.namespaces.faq.innamespace">¿Cómo utilizar las clases
de espacios de nombres, las funciones o las constantes en su propio espacio?</link>
</simpara>
</listitem>
<listitem>
<simpara>
<link linkend="language.namespaces.faq.full">
¿Cómo se resuelve un nombre como <literal>\mon\nom</literal> o
<literal>\nom</literal>?
</link>
</simpara>
</listitem>
<listitem>
<simpara>
<link linkend="language.namespaces.faq.qualified">¿Cómo se resuelve un nombre
como <literal>mon\nom</literal>?</link>
</simpara>
</listitem>
<listitem>
<simpara>
<link linkend="language.namespaces.faq.shortname1">¿Cómo se resuelve un nombre de clase
sin calificación, como <literal>nom</literal>?</link>
</simpara>
</listitem>
<listitem>
<simpara>
<link linkend="language.namespaces.faq.shortname2">¿Cómo se resuelve una función sin
calificación o una constante de nombre <literal>nom</literal>?</link>
</simpara>
</listitem>
</orderedlist>
</para>
<para>
Aquí están los puntos particulares de la implementación, que pueden ser
útiles para la comprensión global.
<orderedlist>
<listitem>
<simpara>
<link linkend="language.namespaces.faq.conflict">Los nombres importados no deben
entrar en conflicto con las clases definidas en el mismo archivo</link>
</simpara>
</listitem>
<listitem>
<simpara>
<link linkend="language.namespaces.faq.nested">Los espacios de nombres anidados
están prohibidos</link>
</simpara>
</listitem>
<listitem>
<simpara>
<link linkend="language.namespaces.faq.quote">Los nombres de espacios de nombres
dinámicos deben proteger el backslash</link>
</simpara>
</listitem>
<listitem>
<simpara>
<link linkend="language.namespaces.faq.constants">Las constantes no definidas
referenciadas con un backslash producen un error fatal</link>
</simpara>
</listitem>
<listitem>
<simpara>
<link linkend="language.namespaces.faq.builtinconst">Imposible reemplazar
constantes especiales como &null;, &true; o &false;</link>
</simpara>
</listitem>
</orderedlist>
</para>
<sect2 xml:id="language.namespaces.faq.shouldicare">
<title>Si no utilizo espacios de nombres, ¿debo preocuparme por ellos?</title>
<para>
No, los espacios de nombres no afectan el código existente, de una
manera u otra, ni el código que se producirá y que no utiliza
espacios de nombres. Puede escribir esto si lo desea:
</para>
<para>
<example>
<title>Acceso a una clase global desde fuera de un espacio de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
$a = new \stdClass;
?>
]]>
</programlisting>
</example>
</para>
<para>
Es una funcionalidad equivalente a:
</para>
<para>
<example>
<title>Acceder a clases globales fuera de un espacio de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
$a = new stdClass;
?>
]]>
</programlisting>
</example>
</para>
</sect2>
<sect2 xml:id="language.namespaces.faq.globalclass">
<title>¿Cómo utilizar una clase global o interna desde un espacio de nombres?</title>
<para>
<example>
<title>Acceso a clases internas desde un espacio de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
namespace foo;
$a = new \stdClass;
function test(\ArrayObject $parameter_type_example = null) {}
$a = \DirectoryIterator::CURRENT_AS_FILEINFO;
// extensión de una clase interna o global
class MyException extends \Exception {}
?>
]]>
</programlisting>
</example>
</para>
</sect2>
<sect2 xml:id="language.namespaces.faq.innamespace">
<title>
¿Cómo utilizar las clases de espacios de nombres, las funciones o
las constantes en su propio espacio?
</title>
<para>
<example>
<title>Acceso a clases, funciones y constantes internas en un espacio de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
namespace foo;
class MaClasse {}
// uso de una clase en el espacio de nombres actual, como tipo de parámetro
function test(MaClasse $parameter_type_example = null) {}
// otra manera de usar una clase en el espacio de nombres actual como tipo de parámetro
function test(\foo\MaClasse $parameter_type_example = null) {}
// extensión de una clase en el espacio de nombres actual
class Extended extends MaClasse {}
// acceso a una función global
$a = \globalfunc();
// acceso a una constante global
$b = \INI_ALL;
?>
]]>
</programlisting>
</example>
</para>
</sect2>
<sect2 xml:id="language.namespaces.faq.full">
<title>
¿Cómo se resuelve un nombre como <literal>\mon\nom</literal> o
<literal>\nom</literal>?
</title>
<para>
Los nombres que comienzan con <literal>\</literal> siempre se resuelven como son,
por lo que <literal>\mon\nom</literal> es en realidad
<literal>mon\nom</literal>, y <literal>\Exception</literal> es
<literal>Exception</literal>.
<example>
<title>Nombres de espacios absolutos</title>
<programlisting role="php">
<![CDATA[
<?php
namespace foo;
$a = new \mon\nom(); // instancia la clase "mon\nom"
echo \strlen('hi'); // llama a la función "strlen"
$a = \INI_ALL; // $a recibe el valor de la constante "INI_ALL"
?>
]]>
</programlisting>
</example>
</para>
</sect2>
<sect2 xml:id="language.namespaces.faq.qualified">
<title>¿Cómo se resuelve un nombre como <literal>mon\nom</literal>?</title>
<para>
Los nombres que contienen un backslash pero no comienzan con un
backslash, como <literal>mon\nom</literal> pueden resolverse de dos maneras
diferentes.
</para>
<para>
Si ha habido una instrucción de importación que hace un alias de
<literal>mon</literal>, entonces el alias importado se aplica en lugar
de <literal>mon</literal>, y el espacio de nombres se convierte en <literal>mon\nom</literal>.
</para>
<para>
De lo contrario, el espacio de nombres actual se agrega antes del camino de la clase
<literal>mon\nom</literal>.
</para>
<para>
<example>
<title>Nombres calificados</title>
<programlisting role="php">
<![CDATA[
<?php
namespace foo;
use blah\blah as foo;
$a = new mon\nom(); // instancia la clase "foo\mon\nom"
foo\bar::name(); // llama al método estático "name" en la clase "blah\blah\bar"
mon\bar(); // llama a la función "foo\mon\bar"
$a = mon\BAR; // asigna a $a el valor de la constante "foo\mon\BAR"
?>
]]>
</programlisting>
</example>
</para>
</sect2>
<sect2 xml:id="language.namespaces.faq.shortname1">
<title>¿Cómo se resuelve un nombre de clase
sin calificación, como <literal>nom</literal>?</title>
<para>
Los nombres de clases que no contienen backslash como
<literal>nom</literal> pueden resolverse de dos maneras diferentes.
</para>
<para>
Si hay una instrucción de importación que define un alias para <literal>nom</literal>,
entonces se aplica el alias.
</para>
<para>
De lo contrario, se utiliza el espacio de nombres actual y se prefiere a
<literal>nom</literal>.
</para>
<para>
<example>
<title>Clases sin calificación</title>
<programlisting role="php">
<![CDATA[
<?php
namespace foo;
use blah\blah as foo;
$a = new nom(); // instancia la clase "foo\nom"
foo::nom(); // llama al método estático "nom" en la clase "blah\blah"
?>
]]>
</programlisting>
</example>
</para>
</sect2>
<sect2 xml:id="language.namespaces.faq.shortname2">
<title>
¿Cómo se resuelve una función sin calificación o una constante
de nombre <literal>nom</literal>?
</title>
<para>
Las funciones y constantes que no tienen backslash en su nombre
como <literal>nom</literal> se resuelven de dos maneras diferentes:
</para>
<para>
Primero, se prefiere el espacio de nombres actual a <literal>nom</literal>.
</para>
<para>
Luego, si la constante o función <literal>nom</literal> no existe
en el espacio de nombres actual, se utiliza la versión global de la constante o la
función <literal>nom</literal>.
</para>
<para>
<example>
<title>Funciones y constantes sin espacio de nombres</title>
<programlisting role="php">
<![CDATA[
<?php
namespace foo;
use blah\blah as foo;
const FOO = 1;
function mon() {}
function foo() {}
function sort(&$a)
{
\sort($a); // Llamada a la función global "sort"
$a = array_flip($a);
return $a;
}
mon(); // llama "foo\mon"
$a = strlen('hi'); // llama a la función global "strlen" ya que "foo\strlen" no existe
$arr = array(1,3,2);
$b = sort($arr); // llama a la función "foo\sort"
$c = foo(); // llama a la función "foo\foo": la importación no se aplica
$a = FOO; // asigna a $a el valor de la constante "foo\FOO": la importación no se aplica
$b = INI_ALL; // asigna a $b el valor de la constante "INI_ALL"
?>
]]>
</programlisting>
</example>
</para>
</sect2>
<sect2 xml:id="language.namespaces.faq.conflict">
<title>Los nombres importados no deben
entrar en conflicto con las clases definidas en el mismo archivo</title>
<para>
La siguiente combinación de scripts es válida:
<informalexample>
<simpara>file1.php</simpara>
<programlisting role="php">
<![CDATA[
<?php
namespace mes\trucs;
class MaClasse {}
?>
]]>
</programlisting>
<simpara>another.php</simpara>
<programlisting role="php">
<![CDATA[
<?php
namespace another;
class untruc {}
?>
]]>
</programlisting>
<simpara>file2.php</simpara>
<programlisting role="php">
<![CDATA[
<?php
namespace mes\trucs;
include 'file1.php';
include 'another.php';
use another\untruc as MaClasse;
$a = new MaClasse; // instancia la clase "untruc" del espacio de nombres another
?>
]]>
</programlisting>
</informalexample>
</para>
<para>
No hay conflicto de nombres, incluso si la clase <literal>MaClasse</literal> existe
en el espacio de nombres <literal>mes\trucs</literal>, ya que la definición de
<literal>MaClasse</literal> está en un archivo separado. Sin embargo, el siguiente
ejemplo produce un error fatal debido a un conflicto de nombres, ya que
<literal>MaClasse</literal> se define en el mismo archivo que la instrucción
<literal>use</literal>.
<informalexample>
<programlisting role="php">
<![CDATA[
<?php
namespace mes\trucs;
use another\untruc as MaClasse;
class MaClasse {} // error fatal: MaClasse está en conflicto con la instrucción de importación
$a = new MaClasse;
?>
]]>
</programlisting>
</informalexample>
</para>
</sect2>
<sect2 xml:id="language.namespaces.faq.nested">
<title>Los espacios de nombres anidados están prohibidos</title>
<para>
PHP no permite anidar espacios de nombres.
<informalexample>
<programlisting role="php">
<![CDATA[
<?php
namespace mes\trucs {
namespace nested {
class foo {}
}
}
?>
]]>
</programlisting>
</informalexample>
Sin embargo, es fácil simular espacios de nombres anidados,
como esto:
<informalexample>
<programlisting role="php">
<![CDATA[
<?php
namespace mes\trucs\nested {
class foo {}
}
?>
]]>
</programlisting>
</informalexample>
</para>
</sect2>
<sect2 xml:id="language.namespaces.faq.quote">
<title>Los nombres de espacios de nombres dinámicos deben proteger el backslash</title>
<para>
Es muy importante darse cuenta de que, como los backslash se utilizan como
caracteres de escape en las cadenas, siempre deben duplicarse
para poder usarlos en una cadena. De lo contrario, existe el riesgo de uso
inesperado:
<example>
<title>Peligros de usar espacios de nombres en una cadena</title>
<programlisting role="php">
<![CDATA[
<?php
$a = "dangereux\nom"; // \n es una nueva línea en una cadena!
$obj = new $a;
$a = 'pas\vraiment\dangereux'; // ningún problema aquí
$obj = new $a;
?>
]]>
</programlisting>
</example>
En una cadena de comillas dobles, la secuencia de escape es mucho más
segura de usar, pero aún se recomienda proteger siempre los backslashs en una cadena que contiene un espacio de nombres.
</para>
</sect2>
<sect2 xml:id="language.namespaces.faq.constants">
<title>Constantes no definidas referenciadas con un backslash producen un error fatal</title>
<para>
Cualquier constante no definida que no tenga calificador como
<literal>FOO</literal> producirá una advertencia: PHP asumía que
<literal>FOO</literal> era el valor de la constante. Cualquier constante,
calificada parcialmente o totalmente, que contenga un backslash, producirá
un error fatal si no está definida.
<example>
<title>Constantes no definidas</title>
<programlisting role="php">
<![CDATA[
<?php
namespace bar;
$a = FOO; // produce una advertencia: constante no definida "FOO", que toma el valor de "FOO";
$a = \FOO; // error fatal, constante de espacio de nombres no definida FOO
$a = Bar\FOO; // error fatal, constante de espacio de nombres no definida bar\Bar\FOO
$a = \Bar\FOO; // error fatal, constante de espacio de nombres no definida Bar\FOO
?>
]]>
</programlisting>
</example>
</para>
</sect2>
<sect2 xml:id="language.namespaces.faq.builtinconst">
<title>Imposible reemplazar constantes especiales como &null;, &true; o &false;</title>
<para>
Cualquier intento en un espacio de nombres de reemplazar las constantes
nativas o especiales, produce un error fatal.
<example>
<title>Constantes que no pueden ser redefinidas</title>
<programlisting role="php">
<![CDATA[
<?php
namespace bar;
const NULL = 0; // error fatal;
const true = 'stupid'; // aún otro error fatal;
// etc.
?>
]]>
</programlisting>
</example>
</para>
</sect2>
</sect1>
</chapter>
<!-- Keep this comment at the end of the file
Local variables:
mode: sgml
sgml-omittag:t
sgml-shorttag:t
sgml-minimize-attributes:nil
sgml-always-quote-attributes:t
sgml-indent-step:1
sgml-indent-data:t
indent-tabs-mode:nil
sgml-parent-document:nil
sgml-default-dtd-file:"~/.phpdoc/manual.ced"
sgml-exposed-tags:nil
sgml-local-catalogs:nil
sgml-local-ecat-files:nil
End:
vim600: syn=xml fen fdm=syntax fdl=2 si
vim: et tw=78 syn=sgml
vi: ts=1 sw=1
-->