Увійти Реєстрація
Блог Серії
Кар'єра
Вакансії Компанії
Навчання
Документація Співбесіди Тестування Відео
Екосистема
Пакети Ресурси Проєкти Інструменти Події
Інше
Про нас Реклама

Як працює yield from і як повернути значення з генератора?

yield from делегує частину генерації іншому генератору чи ітерованому значенню: усі його значення віддаються так, ніби їх видав поточний генератор.

function walk(array $node): Generator
{
    yield $node['path'];

    foreach ($node['children'] as $child) {
        yield from walk($child);    // рекурсивний обхід дерева
    }
}

foreach (walk($tree) as $path) {
    echo $path, PHP_EOL;
}

Працює з генераторами, масивами й будь-яким Traversable.

Повернення значення з генератора: return у генераторі не віддає значення в цикл, а зберігає його як результат - його читають через getReturn() після завершення:

function importRows(iterable $rows): Generator
{
    $imported = 0;

    foreach ($rows as $row) {
        yield $row['id'];      // проміжні результати
        $imported++;
    }

    return $imported;          // підсумок
}

$gen = importRows($rows);
foreach ($gen as $id) { /* ... */ }
echo $gen->getReturn();        // кількість

А yield from повертає результат делегованого генератора:

$count = yield from importRows($rows);

Пастки:

  • Ключі. yield from зберігає ключі делегованого джерела. Два yield from по масивах з ключами 0, 1, 2 дадуть дублікати ключів, і iterator_to_array() перезапише значення. Рішення - iterator_to_array($gen, preserve_keys: false).
  • getReturn() до завершення генератора кидає виняток.
  • Генератор одноразовий: пройти його вдруге не можна.

Двосторонній обмін: $received = yield $value; разом із $gen->send($data) дозволяє передавати дані в генератор - на цьому будували співпрограми до появи Fibers.

Докладніше в документації: Синтаксис генераторів

Перевір себе

20 випадкових питань за спробу, після завершення - розбір кожної помилки

Схожі питання