match

Оновлено: 12.05.2023

(PHP 8)

Вираз match розгалужує обчислення на основі перевірки ідентичності значення. Подібно до оператора switch, вираз збігу має предметний вираз, який порівнюється з кількома альтернативами. На відміну від switch, він обчислює значення, подібно до тернарних виразів. На відміну від switch, порівняння є перевіркою на тотожність (===), а не слабкою перевіркою на рівність (==). Вирази порівняння доступні починаючи з версії PHP 8.0.0.

Приклад #1 Структура виразу співпадіння

<?php
$return_value = match (subject_expression) {
    single_conditional_expression => return_expression,
    conditional_expression1, conditional_expression2 => return_expression,
};
?>

Приклад #2 Базове використання match

<?php
$food = 'cake';

$return_value = match ($food) {
    'apple' => 'This food is an apple',
    'bar' => 'This food is a bar',
    'cake' => 'This food is a cake',
};

var_dump($return_value);
?>

Зауваження: Результат виразу збігу не обов'язково використовувати.

Вираз match схожий на оператор switch, але має деякі ключові відмінності:

  • Вираз порівняння порівнює значення строго (===), а не вільно, як це робить оператор switch.
  • Вираз порівняння повертає значення.
  • Вирази порівняння не переходять до наступних випадків, як це робить оператор switch.
  • Вираз порівняння має бути вичерпним.

Як оператори перемикання, вирази збігу виконуються вираз за виразом, вираз за виразом, вираз за виразом. На початку ніякого коду не виконується. Умовні вирази обчислюються лише тоді, коли всі попередні умовні вирази не збігаються з основним виразом. Буде обчислено лише вираз повернення, який відповідає умовному виразу, що збігається. Наприклад:

<?php
$result = match ($x) {
    foo() => ...,
    $this->bar() => ..., // $this->bar() isn't called if foo() === $x
    $this->baz => beep(), // beep() isn't called unless $x === $this->baz
    // etc.
};
?>

в плечах виразів збігу може міститися кілька виразів, розділених комою. Це логічне АБО і є скороченим позначенням для кількох виразів, що мають однакову праву частину.

<?php
$result = match ($x) {
    // This match arm:
    $a, $b, $c => 5,
    // Is equivalent to these three match arms:
    $a => 5,
    $b => 5,
    $c => 5,
};
?>

Особливим випадком є шаблон за замовчуванням. Цей шаблон відповідає всьому, що не було знайдено раніше. Наприклад:

<?php
$expressionResult = match ($condition) {
    1, 2 => foo(),
    3, 4 => bar(),
    default => baz(),
};
?>

Зауваження: Кілька шаблонів за замовчуванням призведуть до помилки E_FATAL_ERROR.

Вираз зіставлення повинен бути вичерпним. Якщо предметний вираз не обробляється жодною рукою зіставлення, буде згенеровано помилку UnhandledMatchError.

Приклад #3 Приклад необробленого виразу збігу

<?php
$condition = 5;

try {
    match ($condition) {
        1, 2 => foo(),
        3, 4 => bar(),
    };
} catch (\UnhandledMatchError $e) {
    var_dump($e);
}
?>

Для обробки умовних випадків нетотожності можна використовувати вираз збігу, використовуючи true як предметний вираз.

Приклад #4 Використання узагальненого виразу зіставлення для розгалуження на цілочисельних діапазонах

<?php

$age = 23;

$result = match (true) {
    $age >= 65 => 'senior',
    $age >= 25 => 'adult',
    $age >= 18 => 'young adult',
    default => 'kid',
};

var_dump($result);
?>

Приклад #5 Використання узагальненого виразу порівняння для розгалуження вмісту рядка

<?php

$text = 'Bienvenue chez nous';

$result = match (true) {
    str_contains($text, 'Welcome') || str_contains($text, 'Hello') => 'en',
    str_contains($text, 'Bienvenue') || str_contains($text, 'Bonjour') => 'fr',
    // ...
};

var_dump($result);
?>