命名空間其實早在PHP5.3就已經出現了,不過大部分同學可能在各種框架的使用中才會接觸到命名空間的內容,當然,現代化的開發也都離不開這些能夠快速產出的框架,這次我們不從框架的角度,僅從簡單的代碼角度來決議一下命名空間的概念和使用,
首先,我們要定義命名空間是個什么東西,
其實就像作業系統的目錄一樣,命名空間就是為了解決類似于作業系統中同一個檔案夾不能有相同的檔案名一樣的問題,假設我們只有一個檔案,一個目錄,那么在這個目錄中,是不能有兩個完全相同的檔案的,如果有這樣名稱完全相同的檔案,那么作業系統也不知道我們到底應該打開的是哪一個檔案,同理,在一個PHP檔案中,我們也不能起相同名稱的函式或者類名,PHP也不知道我們到底要呼叫的是哪一個函式或者類,
理解了上述內容之后,再來看命名空間的語法,其實非常像我們的目錄的定義,
namespace A\B\C;
這個命名空間的定義就是指出了當前命名空間是A\B\C,就像是C:\A\B\C這樣一個檔案夾一樣,光說不練假把式,直接上代碼來看看:
// file1.php
namespace FILE1;
const CONST_A = 2;
function testA(){
echo 'FILE1\testA()', PHP_EOL;
}
class objectA{
function test(){
echo 'FILE1\ObjectA', PHP_EOL;
}
}
// file2.php
namespace FILE2;
const CONST_A = 3;
function testA(){
echo 'FILE2\testA()', PHP_EOL;
}
class objectA{
function test(){
echo 'FILE2\ObjectA', PHP_EOL;
}
}
我們在namespace目錄下創建了這兩個php檔案,函式和類名都是一樣的,但定義了不同的命名空間,一個是FILE1,一個是FILE2,
namespace A;
include 'namespace/file1.php';
include 'namespace/file2.php';
use FILE1, FILE2;
use FILE1\objectA as objectB;
const CONST_A = 1;
function testA(){
echo 'A\testA()', PHP_EOL;
}
class objectA{
function test(){
echo 'A\ObjectA', PHP_EOL;
}
}
// 當前命名空間
echo CONST_A, PHP_EOL; // 1
testA(); // A\testA()
$oA = new objectA();
$oA->test(); // A\ObjectA
// FILE1
echo FILE1\CONST_A, PHP_EOL; // 2
FILE1\testA(); // FILE1\testA()
$oA = new FILE1\objectA();
$oA->test(); // FILE1\ObjectA
$oB = new objectB();
$oB->test(); // FILE1\ObjectA
// FILE2
echo FILE2\CONST_A, PHP_EOL; // 3
FILE2\testA(); // FILE2\testA()
$oA = new FILE2\objectA();
$oA->test(); // FILE2\ObjectA
在測驗代碼中,我們又定義了當前的命名空間為A,并include了file1.php和file2.php,并在這個檔案中同時也定義了與file1.php和file2.php中相同的函式和類名,接下來我們依次呼叫這些靜態變數、函式和類,
- 在默認情況下,靜態變數、函式、類呼叫的是當前命名空間下的內容
- 在使用了FILE1\和FILE2\之后,呼叫的是就是指定命名空間下的內容
- 需要使用use引入命名空間,否則無法使用命名空間里的內容
- use中可以使用as關鍵字為命名空間或者其中的類指定別名
命名空間的使用其實就是這么的簡單,可以看出我們在不同的命名空間中就可以使用相同的函式或者類名了,這一點正是各類現代化開發框架的基礎,同時也是composer能夠實作的最主要的原因之一,
接下來,我們嘗試一個問題是否符合我們的預期,那就是兩個檔案定義相同的命名空間是否能夠定義相同的類名呢?
// file1-1.php
namespace FILE1;
const CONST_A = 1.1;
function testA(){
echo 'FILE1-1\testA()', PHP_EOL;
}
class objectA{
function test(){
echo 'FILE1-1\ObjectA', PHP_EOL;
}
}
我們定義了一個file1-1.php,并且使用了和file1.php相同的FILE1命名空間,然后和file1.php一起include到測驗代碼中,
include 'namespace/file1.php';
include 'namespace/file1-1.php'; // Cannot redeclare FILE1\testA()
好吧,在運行時直接就報錯,不能重復定義同名的函式名,如果注釋掉函式,那么會繼續報類名不能重復,我們再定義一個file1-2.php,這次還是使用FILE1這個命名空間,但是內容不一樣了,
// file1-2.php
namespace FILE1;
const CONST_A = 1.2;
function testA1_2(){
echo 'FILE1-2\testA()', PHP_EOL;
}
class objectA1_2{
function test(){
echo 'FILE1-2\ObjectA', PHP_EOL;
}
}
這樣當然就沒問題啦,這兩個檔案在同一個命名空間下,但是卻有著不同的能力,這樣是完全OK的操作,
include 'namespace/file1.php';
include 'namespace/file1-2.php';
use FILE1;
// FILE1
echo FILE1\CONST_A, PHP_EOL; // 2
FILE1\testA(); // FILE1\testA()
$oA = new FILE1\objectA();
$oA->test(); // FILE1\ObjectA
// FILE1_2
echo FILE1\CONST_A, PHP_EOL; // 3
FILE1\testA1_2(); // FILE1-2\testA()
$oA = new FILE1\objectA1_2();
$oA->test(); // FILE1-2\ObjectA
測驗代碼:
https://github.com/zhangyue0503/dev-blog/blob/master/php/202001/source/PHP%E4%B8%AD%E5%91%BD%E5%90%8D%E7%A9%BA%E9%97%B4%E6%98%AF%E6%80%8E%E6%A0%B7%E7%9A%84%E5%AD%98%E5%9C%A8%EF%BC%9F%EF%BC%88%E4%B8%80%EF%BC%89.php
參考檔案:
https://www.php.net/manual/zh/language.namespaces.rationale.php
https://www.php.net/manual/zh/language.namespaces.definition.php
===============
關注公眾號:【硬核專案經理】獲取最新文章
添加微信/QQ好友:【xiaoyuezigonggong/149844827】免費得PHP、專案管理學習資料
知乎、公眾號、抖音、頭條搜索【硬核專案經理】
B站ID:482780532
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/265551.html
標籤:PHP
