downloads | documentation | faq | getting help | mailing lists | licenses | wiki | reporting bugs | php.net sites | links | conferences | my php.net

search for in the

Пространства имен и динамические особенности языка> <Описание нескольких пространств имен в одном файле
[edit] Last updated: Fri, 25 May 2012

view this page in

Использование пространства имен: основы

(PHP 5 >= 5.3.0)

До обсуждения использования пространств имен важно понять как PHP узнает какие элементы из пространства имен запрашиваются в вашем коде. Можно провести аналогию между пространствами имен PHP и файловой системой. Есть три способа обратиться к файлу в файловой системе:

  1. Относительное имя файла, такое как foo.txt, преобразуемое в currentdirectory/foo.txt, где currentdirectory текущая директория, в которой мы находимся. Тогда, если текущая директория /home/foo, то имя преобразуется в /home/foo/foo.txt.
  2. Относительное имя пути, такое как subdirectory/foo.txt, преобразуется в currentdirectory/subdirectory/foo.txt.
  3. Абсолютное имя пути, такое как /main/foo.txt, которое остается таким же: /main/foo.txt.
Тот же принцип применим и к элементам из пространств имен PHP. Для примера, имя класса может быть указано тремя способами:
  1. Неполные имена (имена классов без префикса), такие как $a = new foo(); или foo::staticmethod();. Если текущее пространство имен currentnamespace, то эти имена преобразуются в currentnamespace\foo. Если код находится в глобальном пространстве имен, то имена остаются такими же: foo. Предупреждение: неполные имена для функций и констант будут определяться в глобальном пространстве имен, если они не определены в текущем пространстве имен. Подробнее в Использование пространств имен: доступ к глобальным функциям и классам.
  2. Полные имена (имена классов с префиксами), такие как $a = new subnamespace\foo(); или subnamespace\foo::staticmethod();. Если текущее пространство имен currentnamespace, то эти имена преобразуются в currentnamespace\subnamespace\foo. Если код находится в глобальном пространстве имен, то имена преобразуются в subnamespace\foo.
  3. Абсолютные имена или имена с предшествующим префиксом, обозначающим глобальное пространство. $a = new \currentnamespace\foo(); или \currentnamespace\foo::staticmethod();. Имена всегда определяются также как и записаны: currentnamespace\foo.

Ниже приведен пример трех вариантов синтаксиса в реальном коде:

file1.php

<?php
namespace Foo\Bar\subnamespace;

const 
FOO 1;
function 
foo() {}
class 
foo
{
    static function 
staticmethod() {}
}
?>

file2.php

<?php
namespace Foo\Bar;
include 
'file1.php';

const 
FOO 2;
function 
foo() {}
class 
foo
{
    static function 
staticmethod() {}
}

/* Неполные имена */
foo(); // определяется как функция Foo\Bar\foo
foo::staticmethod(); // определяется как класс Foo\Bar\foo с методом staticmethod
echo FOO// определяется как константа Foo\Bar\FOO

/* Полные имена */
subnamespace\foo(); // определяется как функция Foo\Bar\subnamespace\foo
subnamespace\foo::staticmethod(); // определяется как класс Foo\Bar\subnamespace\foo
                                  // c методом 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
?>

Обратите внимание, что для доступа к любым глобальным классам, функциям или константам, может использоваться абсолютное имя, такое как \strlen(), или \Exception, или \INI_ALL.

Пример #1 Доступ к глобальным классам, функциям и константам из пространства имен

<?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
?>



add a note add a note User Contributed Notes Использование пространства имен: основы
tom at tomwardrop dot com 26-Feb-2012 10:06
It seems the file system analogy only goes so far. One thing that's missing that would be very useful is relative navigation up the namespace chain, e.g.

<?php
namespace MyProject
{
   class
Person {}
}

namespace MyProjectPeople {
    class
Adult extends ..Person {}
}
?>

That would be really nice, especially if you had really deep namespaces. It would save you having to type out the full namespace just to reference a resource one level up.
Lukas Z 05-Dec-2011 03:25
Well variables inside namespaces do not override others since variables are never affected by namespace but always global:
"Although any valid PHP code can be contained within a namespace, only four types of code are affected by namespaces: classes, interfaces, functions and constants. "

Source: "Defining Namespaces"
http://www.php.net/manual/en/language.namespaces.definition.php
philip dot preisser at arcor dot de 14-Jun-2011 02:34
Working with variables can overwrite equal variables in other namespaces

<?php // php5 - package-version : 5.3.5-1ubuntu7.2

   
namespace
    main
   
{}

   
namespace
    mainsub1
   
{
       
$data = 1;
    }

   
namespace
    mainsub2
   
{
        echo
$data;// 1
       
$data = 2;
    }

   
namespace
    mainsub1
   
{
        echo
$data;// 2
       
$data = 1;
    }

   
namespace
   
{
        echo
$data;// 1
   
}

?>
Franois Vespa 21-Dec-2010 05:42
It seems you cannot nest a constant declaration within a if statement

<?php

namespace FOO
;

if(eval)
const
BAR=true;

// will throw the following error:
// PHP Parse error:  syntax error, unexpected T_CONST

// instead use:

if(eval)
define('FOO\BAR',true);

?>
thinice at gmail.com 01-Dec-2010 10:10
Unfortunately as of 5.3.3, it's not possible to do something like:

<?php

namespace Animal
{
  require
'Bovine.php';
  require
'Canine.php';
}

?>

Which could be quite handy for  a handful of reasons.
kukoman at pobox dot sk 17-Oct-2008 11:20
PHP 5.3.0alpha2 (cli)
<?php
//  namespace MyProject\DB;
require 'db.php';

use
MyProjectDB; // fine; same as DB\
use MyProjectDBConnection as DBC; // fine
use MyProjectDB as HM; // fine
use HMConnection as DBC2; // class call ends with FATAL!!!

$x = new DBC(); // fine
$y = new HMConnection(); // fine
$z = new DBC2(); // Fatal error: Class 'HM\Connection' not found
?>
richard at richard-sumilang dot com 27-Mar-2008 01:36
Syntax for extending classes in namespaces is still the same.

Lets call this Object.php:

<?php

namespace comrsumilangcommon
;

class
Object{
  
// ... code ...
}

?>

And now lets create a class called String that extends object in String.php:

<?php

class String extends comrsumilangcommonObject{
  
// ... code ...
}

?>

Now if you class String was defined in the same namespace as Object then you don't have to specify a full namespace path:

<?php

namespace comrsumilangcommon
;

class
String extends Object
{
  
// ... code ...
}

?>

Lastly, you can also alias a namespace name to use a shorter name for the class you are extending incase your class is in seperate namespace:

<?php

namespace comrsumilangutil
;
use
comrsumlangcommon as Common;

class
String extends CommonObject
{
  
// ... code ...
}

?>

- Richard Sumilang

 
show source | credits | stats | sitemap | contact | advertising | mirror sites