W3docs

yield from

La palabra clave yield from en PHP delega la generación de valores a otro generador, permitiendo encadenar múltiples generadores de forma eficiente.

Introducción

yield from es una expresión que permite a un generador delegar a otro iterable — otro generador, un array o cualquier Traversable. En lugar de iterar sobre la fuente interna y volver a producir cada elemento manualmente, se escribe un solo yield from y PHP reenvía todos sus valores (y claves) al llamador automáticamente.

Esto facilita la composición de generadores: puedes construir un flujo grande de valores a partir de pequeñas funciones generadoras enfocadas sin materializar nunca toda la secuencia en memoria. Introducido en PHP 7.0, yield from es la forma estándar de aplanar generadores anidados.

Este capítulo cubre la sintaxis básica, cómo se manejan las claves, cómo capturar el valor de retorno de un generador delegado y cuándo la delegación es la herramienta adecuada.

Sintaxis básica

yield from aparece dentro de una función generadora y va seguido de cualquier iterable:

yield from $iterable; // generator, array, or Traversable

Aquí hay un ejemplo mínimo que combina dos generadores en un solo flujo:

<?php

function myGenerator()
{
  yield "Hello";
  yield "World";
}

function myOtherGenerator()
{
  yield "!";
}

function myCombinedGenerator()
{
  yield from myGenerator();
  yield from myOtherGenerator();
}

foreach (myCombinedGenerator() as $value) {
  echo $value . " ";
}

myCombinedGenerator() no produce ningún valor propio — delega completamente a los otros dos generadores. Al llamarlo, primero produce los valores de myGenerator() y luego los de myOtherGenerator(), por lo que el foreach imprime:

Hello World !

Puedes mezclar libremente la delegación con sentencias yield normales en la misma función:

<?php

function countToThree()
{
  yield 1;
  yield 2;
  yield 3;
}

function countToFive()
{
  yield from countToThree(); // delegates 1, 2, 3
  yield 4;                    // then yields its own values
  yield 5;
}

foreach (countToFive() as $value) {
  echo $value . " ";
}
// Output: 1 2 3 4 5

Delegación a arrays y otros iterables

La fuente tras yield from no tiene que ser un generador. Cualquier array o Traversable funciona, lo que es útil para aplanar secuencias fijas y perezosas juntas:

<?php

function items()
{
  yield from ['apple', 'banana']; // an array
  yield from ['cherry'];
}

foreach (items() as $item) {
  echo $item . "\n";
}
// Output:
// apple
// banana
// cherry

Cómo se manejan las claves

yield from conserva las claves del iterable interno, no solo los valores. Este es el error más común: las claves no se renumeran, por lo que dos fuentes delegadas pueden producir claves duplicadas.

<?php

function inner()
{
  yield 'a' => 1;
  yield 'b' => 2;
}

function outer()
{
  yield from inner();
  yield 'c' => 3;
}

foreach (outer() as $key => $value) {
  echo "$key => $value\n";
}
// Output:
// a => 1
// b => 2
// c => 3

Dado que las claves se mantienen tal cual, no dependas de una secuencia continua 0, 1, 2, … al delegar a fuentes con claves enteras — recopila los valores en un array con iterator_to_array($gen, false) si necesitas reindexarlos.

Capturar el valor de retorno del generador interno

Un generador delegado puede return un valor final (separado de los valores que produce). La expresión yield from evalúa a ese valor de retorno, que puedes asignar a una variable:

<?php

function inner()
{
  yield 1;
  yield 2;
  return 'done';
}

function outer()
{
  $result = yield from inner();
  echo "Inner returned: $result\n";
  yield 3;
}

foreach (outer() as $value) {
  echo "Value: $value\n";
}
// Output:
// Value: 1
// Value: 2
// Inner returned: done
// Value: 3

Ten en cuenta que el valor de return del generador interno es capturado por yield fromno se reenvía al bucle foreach. Solo los valores producidos (1, 2, 3) llegan al consumidor.

Cuándo usar yield from

Usa yield from cuando quieras:

  • Componer generadores — construir un pipeline a partir de pequeñas funciones generadoras de un solo propósito en lugar de una función grande.
  • Aplanar estructuras anidadas — recorrer árboles o arrays anidados de forma recursiva y emitir un único flujo plano de valores.
  • Mantener la eficiencia de memoria — los valores fluyen de forma perezosa, uno a la vez, por lo que nunca se mantiene toda la secuencia en memoria.

Comparado con volver a producir manualmente (foreach ($inner as $v) { yield $v; }), yield from es más corto, preserva las claves automáticamente y reenvía el valor de retorno del generador interno — así que prefiérelo siempre que estés delegando a otro iterable.

Temas relacionados

  • yield — la base de los generadores en PHP.
  • foreach loop — cómo se consumen los valores de los generadores.
  • PHP functions y return — los bloques de construcción detrás de las funciones generadoras.

Práctica

Práctica
¿Cuál es el uso principal de la sentencia 'yield from' en PHP?
¿Cuál es el uso principal de la sentencia 'yield from' en PHP?
Was this page helpful?