列舉類似於類別,並與類別、介面和特質共享相同的命名空間。它們也可以以相同的方式自動載入。列舉定義了一個新的型別,該型別具有固定且有限數量的可能合法值。
<?php
enum Suit
{
case Hearts;
case Diamonds;
case Clubs;
case Spades;
}
?>
此宣告建立了一個名為 Suit
的新列舉型別,它只有四個合法值:Suit::Hearts
、Suit::Diamonds
、Suit::Clubs
和 Suit::Spades
。變數可以被賦予這些合法值之一。函式可以根據列舉型別進行型別檢查,在這種情況下,只能傳遞該型別的值。
<?php
function pick_a_card(Suit $suit)
{
/* ... */
}
$val = Suit::Diamonds;
// OK
pick_a_card($val);
// OK
pick_a_card(Suit::Clubs);
// TypeError: pick_a_card(): Argument #1 ($suit) must be of type Suit, string given
pick_a_card('Spades');
?>
列舉可以有零個或多個 case
定義,沒有上限。零個 case 的列舉在語法上有效,但相當無用。
對於列舉的 case,其語法規則與 PHP 中的任何標籤相同,請參閱 常數。
預設情況下,case 本質上不以純量值作為後盾。也就是說,Suit::Hearts
不等於 "0"
。相反,每個 case 都由該名稱的單例物件作為後盾。這意味著
<?php
$a = Suit::Spades;
$b = Suit::Spades;
$a === $b; // true
$a instanceof Suit; // true
?>
這也意味著列舉值永遠不會彼此 <
或 >
,因為這些比較對物件沒有意義。當使用列舉值時,這些比較將始終返回 false
。
這種沒有相關資料的 case 稱為「純粹 case」。僅包含純粹 case 的列舉稱為純粹列舉。
所有純粹 case 都以其列舉型別的實例實現。列舉型別在內部表示為類別。
所有 case 都有一個唯讀屬性 name
,它是 case 本身的區分大小寫的名稱。
<?php
print Suit::Spades->name;
// prints "Spades"
?>
如果名稱是動態取得的,也可以使用 defined() 和 constant() 函數來檢查或讀取列舉 case 的存在。然而,不建議這樣做,因為對於大多數用例,應該使用 具備值域的列舉。