If you are testing your code at the CLI, note that namespace aliases do not work!
(Before I go on, all the backslashes in this example are changed to percent signs because I cannot get sensible results to display in the posting preview otherwise. Please mentally translate all percent signs henceforth as backslashes.)
Suppose you have a class you want to test in myclass.php:
<?php
namespace my%space;
class myclass {
// ...
}
?>
and you then go into the CLI to test it. You would like to think that this would work, as you type it line by line:
require 'myclass.php';
use my%space%myclass; // should set 'myclass' as alias for 'my%space%myclass'
$x = new myclass; // FATAL ERROR
I believe that this is because aliases are only resolved at compile time, whereas the CLI simply evaluates statements; so use statements are ineffective in the CLI.
If you put your test code into test.php:
<?php
require 'myclass.php';
use my%space%myclass;
$x = new myclass;
//...
?>
it will work fine.
I hope this reduces the number of prematurely bald people.
(PHP 5 >= 5.3.0)
Utilisation des espaces de noms : importation et alias
La capacité de faire référence à un nom absolu avec un alias ou en important un espace de noms est stratégique. C'est un avantage similaire aux liens symboliques dans un système de fichiers.
Les espaces de noms PHP supportent trois types d'alias ou d'importation : l'alias de nom de classe, l'alias de nom d'interface, et l'alias d'espace de noms. Notez que l'importation de constantes ou fonctions n'est pas supportée.
En PHP, l'alias est créé avec l'opérateur use. Voici un exemple qui présente les trois types d'importation :
Exemple #1 importation et alias avec l'opérateur use
<?php
namespace foo;
use My\Full\Classname as Another;
// Ceci est la même chose que use My\Full\NSname as NSname
use My\Full\NSname;
// importation d'une classe globale
use ArrayObject;
$obj = new namespace\Another; // instantie un objet de la classe foo\Another
$obj = new Another; // instantie un objet de la classe My\Full\Classname
NSname\subns\func(); // appelle la fonction My\Full\NSname\subns\func
$a = new ArrayObject(array(1)); // instantie un objet de la classe ArrayObject
// Sans l'instruction "use ArrayObject" nous aurions instantié un objet de la classe foo\ArrayObject
?>
De plus, PHP supporte des raccourcis pratiques, tels que les commandes use multiples.
Exemple #2 importation et alias multiples avec l'opérateur use
<?php
use My\Full\Classname as Another, My\Full\NSname;
$obj = new Another; // instantie un objet de la classe My\Full\Classname
NSname\subns\func(); // appelle la fonction My\Full\NSname\subns\func
?>
L'importation est réalisée à la compilation, ce qui fait que cela n'affecte pas les classes, fonctions et constantes dynamiques.
Exemple #3 Importation et noms d'espaces dynamiques
<?php
use My\Full\Classname as Another, My\Full\NSname;
$obj = new Another; // instantie un objet de la classe My\Full\Classname
$a = 'Another';
$obj = new $a; // instantie un objet de la classe Another
?>
De plus, l'importation n'affecte que les noms sans qualification. Les noms absolus restent absolus, et inchangés par un import.
Exemple #4 Importation et noms d'espaces absolus
<?php
use My\Full\Classname as Another, My\Full\NSname;
$obj = new Another; // instantie un objet de la classe My\Full\Classname
$obj = new \Another; // instantie un objet de la classe Another
$obj = new Another\untruc; // instantie un objet de la classe My\Full\Classname\untruc
$obj = new \Another\untruc; // instantie un objet de la classe Another\untruc
?>
Règles de contextes pour l'importation
Le mot-clé use doit être déclaré dans le contexte le plus externe d'un fichier (le contexte global) ou alors dans les déclarations d'espace de noms. Ceci car l'importation est effectuée à la compilation et non durant l'éxecution, donc on ne peut empiler les contextes. L'exemple qui suit montre des utilisation incorrectes du mot-clé use:
Exemple #5 Règles d'importation incorrectes
<?php
namespace Languages;
class Greenlandic
{
use Languages\Danish;
...
}
?>
Note:
Les règles d'importation sont basées sur les fichiers, ce qui signifie que les fichiers inclus n'hériteront PAS des règles d'importation du fichier parent.
Something that is not immediately obvious, particular with PHP 5.3, is that namespace resolutions within an import are not resolved recursively. i.e.: if you alias an import and then use that alias in another import then this latter import will not be fully resolved with the former import.
For example:
use \Controllers as C;
use C\First;
use C\Last;
Both the First and Last namespaces are NOT resolved as \Controllers\First or \Controllers\Last as one might intend.
You are allowed to "use" the same resource multiple times as long as it is imported under a different alias at each invocation.
For example:
<?php
use Lend;
use Lend\l1;
use Lend\l1 as l3;
use Lend\l2;
use Lend\l1\Keller;
use Lend\l1\Keller as Stellar;
use Lend\l1\Keller as Zellar;
use Lend\l2\Keller as Dellar;
...
?>
In the above example, "Keller", "Stellar", and "Zellar" are all references to "\Lend\l1\Keller", as are "Lend\l1\Keller", "l1\Keller", and "l3\Keller".
Note that you can not alias global namespace:
use \ as test;
echo test\strlen('');
won't work.
The "use" keyword can not be declared inside the function or method. It should be declared as global, after the "namespace" as:
<?php
namespace mydir;
// works perfectly
use mydir/subdir/Class1 as Class1;
function fun1()
{
// Parse error: syntax error, unexpected T_USE
use mydir/subdir/Class1 as Class1;
}
class Class2
{
public function fun2()
{
// Parse error: syntax error, unexpected T_USE
use mydir/subdir/Class1 as Class1;
}
}
?>
(All the backslashes in namespaces are slashes because I can't figure out how to post backslashes here.)
You can have the same "use" for a class and a namespace. For example, if you have these files:
<?php
// foo/bar.php
namespace foo;
class bar
{
public function __toString ()
{
return 'foo\bar\__toString()';
}
}
?>
<?php
// foo/bar/MyClass.php
namespace foo/bar;
class MyClass
{
public function __toString ()
{
return 'foo\bar\MyClass\__toString()';
}
}
?>
In another namespace, you can do:
<?php
namespace another;
require_once 'foo/bar.php';
require_once 'foo/bar/MyClass.php';
use foo/bar;
$bar = new bar();
echo $bar."\n";
$class = new bar/MyClass();
echo $class."\n";
?>
And it will makes the following output:
foo\bar\__toString()
foo\bar\MyClass\__toString()
The last example on this page shows a possibly incorrect attempt of aliasing, but it is totally correct to import a trait \Languages\Languages\Danish.
Because imports happen at compile time, there's no polymorphism potential by embedding the use keyword in a conditonal.
e.g.:
<?php
if ($objType == 'canine') {
use Animal\Canine as Beast;
}
if ($objType == 'bovine') {
use Animal\Bovine as Beast;
}
$oBeast = new Beast;
$oBeast->feed();
?>
