自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

PHP命名空間規(guī)則解析及高級功能

譯文
開發(fā) 后端
日前發(fā)布的PHP 5.3中,最重要的一個新特性就是命名空間的加入。本文介紹了PHP命名空間的一些術(shù)語,其解析規(guī)則,以及一些高級功能的應用,希望能夠幫助讀者在項目中真正使用命名空間。

【51CTO精選譯文】在第一部分中我們介紹了PHP命名空間的用途和namespace關(guān)鍵字,在這篇文章中我們將介紹一下use命令的使用以及PHP如何解析命名空間的名字的。

為了便于對比,我定義了兩個幾乎一樣的代碼塊,只有命名空間的名字不同。

lib1.php

  1. < ?php  
  2. // application library 1  
  3. namespace App\Lib1;  
  4.  
  5. const MYCONST = 'App\Lib1\MYCONST';  
  6.  
  7. function MyFunction() {  
  8.  return __FUNCTION__;  
  9. }  
  10.  
  11. class MyClass {  
  12.  static function WhoAmI() {  
  13. eturn __METHOD__;  
  14.  }  
  15. }  
  16. ?>  

lib2.php

  1. < ?php  
  2. // application library 2  
  3. namespace App\Lib2;  
  4.  
  5. const MYCONST = 'App\Lib2\MYCONST';  
  6.  
  7. function MyFunction() {  
  8.  return __FUNCTION__;  
  9. }  
  10.  
  11. class MyClass {  
  12.  static function WhoAmI() {  
  13. eturn __METHOD__;  
  14.  }  
  15. }  
  16. ?>  

開始之前先要理解幾個PHP命名空間相關(guān)術(shù)語。

◆完全限定名稱(Fully-qualified name)

任何PHP代碼都可以引用完全限定名稱,它是一個以命名空間反斜線開頭的標識符,如\App\Lib1\MYCONST,\App\Lib2\MyFunction( )等。

完全限定名稱是沒有任何歧義的,開頭的反斜線和文件路徑的作用有點類似,它表示“根”全局空間,如果我們在全局空間中實現(xiàn)了一個不同的MyFunction( ),可以使用\MyFunction( )從lib1.php或lib2.php調(diào)用它。

完全限定名稱對一次性函數(shù)調(diào)用或?qū)ο蟪跏蓟浅S杏?,但當你產(chǎn)生了大量的調(diào)用時它們就沒有實用價值了,在下面的討論中我們將會看到,PHP提供了其它選項以解除我們?yōu)槊臻g打字的煩惱。

◆限定名稱(Qualified name)

至少有一個命名空間分隔符的標識符,如Lib1\MyFunction( )。

◆非限定名稱(Unqualified name)

沒有命名空間分隔符的標識符,如MyFunction( )。

在相同的命名空間內(nèi)工作

仔細思考下面的代碼:

myapp1.php

  1. < ?php  
  2. namespace App\Lib1;  
  3.  
  4. require_once('lib1.php');  
  5. require_once('lib2.php');  
  6.  
  7. header('Content-type: text/plain');  
  8. echo MYCONST . "\n";  
  9. echo MyFunction() . "\n";  
  10. echo MyClass::WhoAmI() . "\n";  
  11. ?>  

即使我們同時包括了lib1.php和lib2.php,MYCONST,MyFunction和MyClass標識符只能在lib1.php中引用,這是因為myapp1.php的代碼在相同的App\Lib1命名空間內(nèi)。

執(zhí)行結(jié)果:

  1. App\Lib1\MYCONST  
  2. App\Lib1\MyFunction  
  3. App\Lib1\MyClass::WhoAmI  

命名空間導入

可以使用use操作符導入命名空間,如:

myapp2.php

  1. < ?php  
  2. use App\Lib2;  
  3.  
  4. require_once('lib1.php');  
  5. require_once('lib2.php');  
  6.  
  7. header('Content-type: text/plain');  
  8. echo Lib2\MYCONST . "\n";  
  9. echo Lib2\MyFunction() . "\n";  
  10. echo Lib2\MyClass::WhoAmI() . "\n";  
  11. ?>  

可以定義任意數(shù)量的use語句,或使用逗號分隔成獨立的命名空間,在這個例子中我們導入了App\Lib2命名空間,但我們?nèi)匀徊荒苤苯右肕YCONST,MyFunction和MyClass,因為我們的代碼還在全局空間中,但如果我們添加了“Lib2\”前綴,它們就變成限定名稱了,PHP將會搜索導入的命名空間,直到找到匹配項。

執(zhí)行結(jié)果:

  1. App\Lib2\MYCONST  
  2. App\Lib2\MyFunction  
  3. App\Lib2\MyClass::WhoAmI 

命名空間別名

命名空間別名可能是最有用的構(gòu)想了,別名允許我們使用較短的名稱引用很長的命名空間。

myapp3.php

  1. < ?php  
  2. use App\Lib1 as L;  
  3. use App\Lib2\MyClass as Obj;  
  4.  
  5. header('Content-type: text/plain');  
  6. require_once('lib1.php');  
  7. require_once('lib2.php');  
  8.  
  9. echo L\MYCONST . "\n";  
  10. echo L\MyFunction() . "\n";  
  11. echo L\MyClass::WhoAmI() . "\n";  
  12. echo Obj::WhoAmI() . "\n";  
  13. ?>  

第一個use語句將App\Lib1定義為“L”,任何使用“L”的限定名稱在編譯時都會被翻譯成“App\Lib1”,因此我們就可以引用L\MYCONST和L\MyFunction而不是完全限定名稱了。

第二個use語句定義了“obj”作為App\Lib2\命名空間中MyClass類的別名,這種方式只適合于類,不能用于常量和函數(shù),現(xiàn)在我們就可以使用new Obj( )或象上面那樣運行靜態(tài)方法了。

執(zhí)行結(jié)果:

  1. App\Lib1\MYCONST  
  2. App\Lib1\MyFunction  
  3. App\Lib1\MyClass::WhoAmI  
  4. App\Lib2\MyClass::WhoAmI  

PHP命名解析規(guī)則

PHP標識符名稱使用下列命名空間規(guī)則進行解析,請參考PHP用戶手冊了解更詳細的信息:

1.在編譯時調(diào)用完全限定函數(shù)、類或常量;

2.非限定名稱和限定名稱根據(jù)導入規(guī)則進行翻譯,例如,如果A\B\C導入為C,調(diào)用C\D\e( )就會被翻譯成A\B\C\D\e( );

3.在PHP命名空間內(nèi),所有限定名稱尚未根據(jù)導入規(guī)則轉(zhuǎn)換,例如,如果在命名空間A\B中調(diào)用C\D\e( ),那么會被翻譯成A\B\C\D\e( );

4.非限定類名稱根據(jù)當前的導入規(guī)則進行轉(zhuǎn)換,使用全名替換導入的短名稱,例如,如果類C在命名空間A\B中被導入為X,那么new X( )就會被翻譯為new A\B\C( );

5.在命名空間中非限定函數(shù)調(diào)用在運行時解析,例如,如果MyFunction( )在命名空間A\B中被調(diào)用,PHP首先會查找函數(shù)\A\B\MyFunction( ),如果沒有找到,然后會在全局空間中查找\MyFunction( );

6.調(diào)用非限定或限定類名在運行時被解析,例如,如果我們在命名空間A\B中調(diào)用new C( ),PHP將會查找類A\B\C,如果沒有找到,PHP會嘗試自動載入A\B\C。

#p#

PHP命名空間高級特性

接下來讓我們看一看PHP命名空間的一些高級特性。

__NAMESPACE__常量

__NAMESPACE__是一個PHP字符串,它總是返回當前命名空間的名稱,在全局空間中它是一個空字符串。

  1. < ?php  
  2. namespace App\Lib1;  
  3. echo __NAMESPACE__; // outputs: App\Lib1  
  4. ?>  
  5.  

這個值在調(diào)試時非常有用,它也可由于動態(tài)生成一個完全限定類名,如:

  1. < ?php  
  2. namespace App\Lib1;  
  3.  
  4. class MyClass {  
  5.  public function WhoAmI() {  
  6. return __METHOD__;  
  7.  }  
  8. }  
  9.  
  10. $c = __NAMESPACE__ . '\\MyClass';  
  11. $m = new $c;  
  12. echo $m->WhoAmI(); // outputs: App\Lib1\MyClass::WhoAmI  
  13. ?>  

namespace關(guān)鍵字

namespace關(guān)鍵字可以用于明確引用一個當前命名空間或子命名空間中的項目,它等價于類中的self命名空間:

  1. < ?php  
  2. namespace App\Lib1;  
  3.  
  4. class MyClass {  
  5.  public function WhoAmI() {  
  6. return __METHOD__;  
  7.  }  
  8. }  
  9.  
  10. $m = new namespace\MyClass;  
  11. echo $m->WhoAmI(); // outputs: App\Lib1\MyClass::WhoAmI  
  12. ?>  

自動載入命名空間類

PHP 5中最省時省力的特性是自動載入,在全局(非命名空間)PHP代碼中,可以寫一個標準自動載入函數(shù):

  1. < ?php  
  2. $objnew MyClass1(); // classes/MyClass1.php is auto-loaded  
  3. $objnew MyClass2(); // classes/MyClass2.php is auto-loaded  
  4.  
  5. // autoload function  
  6. function __autoload($class_name) {  
  7.  require_once("classes/$class_name.php");  
  8. }  
  9. ?>  

在PHP 5.3中,你可以創(chuàng)建一個命名空間類的實例,在這種情況下,完全限定命名空間和類名傳遞給__autoload函數(shù),例如,$class_name的值可能是App\Lib1\MyClass。你可以在相同的文件夾下放置所有的PHP類文件,從字符串中提取命名空間,但那樣會導致文件名沖突。

另外,你的類文件層次結(jié)構(gòu)會按照命名空間的結(jié)構(gòu)重新組織,例如,MyClass.php文件可以創(chuàng)建在/classes/App/Lib1文件夾下:

/classes/App/Lib1/MyClass.php

  1. < ?php  
  2. namespace App\Lib1;  
  3.  
  4. class MyClass {  
  5.  public function WhoAmI() {  
  6. return __METHOD__;  
  7.  }  
  8. }  
  9. ?>  

在根文件夾下的文件就使用下面的代碼了:

myapp.php

  1. < ?php  
  2. use App\Lib1\MyClass as MC;  
  3.  
  4. $obj = new MC();  
  5. echo $obj->WhoAmI();  
  6.  
  7. // autoload function  
  8. function __autoload($class) {  
  9.  // convert namespace to full file path  
  10.  $class = 'classes/' . str_replace('\\', '/', $class) . '.php';  
  11.  require_once($class);  
  12. }  
  13. ?>  

解釋:

1.類App\Lib1\MyClass的別名是MC;

2. new MC( )在編譯時被翻譯成new App\Lib1\MyClass( );

3.字符串App\Lib1\MyClass被傳遞給__autoload函數(shù),使用文件路徑正斜線替換所有命名空間中的反斜線,然后修改字符串,classes\App\Lib1\MyClass.php文件被自動載入;

總結(jié)

有關(guān)PHP命名空間的使用就介紹到這里,希望您能夠?qū)HP的命名空間有一個新的認識,并希望你能在新項目中真正使用命名空間。

原文:How to Use PHP Namespaces

作者:Craig Buckler

【編輯推薦】

  1. PHP 5.3中的命名空間:你用過了么?
  2. PHP 5.3中的命名空間使用方法淺述
  3. PHP 5.3.0發(fā)布 新增命名空間等多項特性
  4. PHP的命名空間
  5. PHP 5.3閉包語法初探
責任編輯:yangsai 來源: 51CTO.com
相關(guān)推薦

2009-11-18 16:58:55

PHP命名規(guī)則

2010-07-05 16:33:00

PHPPHP命名空間

2010-08-06 10:41:59

Flex命名空間

2009-09-21 08:50:42

.NET中文變量

2009-07-20 10:18:49

PHP 5.3命名空間

2011-03-16 14:23:38

分布式文件

2009-07-01 09:32:11

PHP 5.3.0

2010-01-12 17:32:49

H3C交換機命名規(guī)則

2010-09-01 13:44:23

idclassCSS

2009-07-17 09:31:06

PHP 5.3命名空間

2010-08-25 09:11:57

DIVCSS

2012-08-24 09:05:30

IBMdW

2010-09-07 15:53:02

CSS規(guī)范化

2010-09-08 16:49:05

CSSclassid

2010-08-30 10:46:13

DIV+CSS

2009-09-11 09:22:14

System.Linq

2013-08-21 16:48:42

.Net命名空間

2009-08-28 13:56:25

C#反射命名空間

2009-08-27 15:34:38

C#命名空間

2009-08-12 10:46:54

C#命名空間
點贊
收藏

51CTO技術(shù)棧公眾號