PHP 8 正式發佈及新特性,性能提升 10%
最近更新時間 2020-11-28 15:21:15
PHP 8 於2020年11月26日發佈,這是一個主版本更新,意味着更多的新功能和性能優化。新特性包括命名參數、聯合類型、註解、構造器屬性提升、match 表達式、nullsafe 運算符、JIT、並改進了類型系統、錯誤處理、語法一致性。
新特性
命名參數(Named arguments)
命名參數允許參數傳值時指定名稱,因此不必考慮參數順序,可以直接忽略可選參數。
#函數定義
function foo(string $a, string $b, ?string $c = null, ?string $d = null)
{ /* … */ }
#調用函數
foo(
b: 'value b',
a: 'value a',
d: 'value d',
);
註解(Attributes)
可以用 PHP 原生語法來使用結構化的元數據,而非 PHPDoc 聲明。
use App\Attributes\ExampleAttribute;
#[ExampleAttribute]
class Foo
{
#[ExampleAttribute]
public const FOO = 'foo';
#[ExampleAttribute]
public $x;
#[ExampleAttribute]
public function foo(#[ExampleAttribute] $bar) { }
}
構造器屬性提升(Constructor property promotion)
可以在構造函數中直接定義類的屬性類型,不必再分開定義,如下所示:
#PHP 7
class Point {
public float $x;
public float $y;
public float $z;
public function __construct(
float $x = 0.0,
float $y = 0.0,
float $z = 0.0,
) {
$this->x = $x;
$this->y = $y;
$this->z = $z;
}
}
#PHP 8
class Point {
public function __construct(
public float $x = 0.0,
public float $y = 0.0,
public float $z = 0.0,
) {}
}
聯合類型(Union types)
聯合類型表示一個變量可以指定兩個或以上的類型。void 不能用作聯合類型。nullable 可通過 |null 表示,還可使用 ? 符號。
public function foo(Foo|null $foo): void;
public function bar(?Bar $bar): void;
Match 表達式(Match expression)
Math 表達式類似 switch 語句,可以直接返回結果無需 break 語句,和合並多個條件語句,Math 使用嚴格比較。如下所示:
$result = match($input) {
0 => "hello",
'1', '2', '3' => "world",
};
Nullsafe 運算符(Nullsafe operator)
傳統空合併運算符有個很大缺點,需要進行大量檢測判斷。可以用新的 Nullsafe 運算符鏈式調用,而不需要條件檢查 null。 如果鏈條中的一個元素失敗了,整個鏈條會中止並認定為 Null。
#PHP 7
$country = null;
if ($session !== null) {
$user = $session->user;
if ($user !== null) {
$address = $user->getAddress();
if ($address !== null) {
$country = $address->country;
}
}
}
#PHP 8
$country = $session?->user?->getAddress()?->country;
數字和字符串的比較
PHP 8 比較數字和字符串時,會按數字進行比較。不是數字字符串時,將數字轉化為字符串,按字符串比較。
#PHP 7
0 == 'foobar' // true
#PHP 8
0 == 'foobar' // false
錯誤異常
PHP 8 中大多數內部函數在參數驗證失敗時拋出 Error 級異常。
#PHP 7
strlen([]); // Warning: strlen() expects parameter 1 to be string, array given
array_chunk([], -1); // Warning: array_chunk(): Size parameter expected to be greater than 0
#PHP 8
strlen([]); // TypeError: strlen(): Argument #1 ($str) must be of type string, array given
array_chunk([], -1); // ValueError: array_chunk(): Argument #2 ($length) must be greater than 0
即時編譯(JIT)
PHP 8 中包含兩個即時編譯引擎 Tracing JIT 和 Function JIT,Tracing JIT 在兩個中更有潛力,它在綜合基準測試中顯示了三倍的性能, 並在某些長時間運行的程序中顯示了 1.5-2 倍的性能改進。如下圖所示: