Generator-Syntax

Eine Generatorfunktion sieht genau so aus wie eine normale Funktion mit der Ausnahme, dass ein Generator statt eines Wertes so viele Werte wie nötig zurückgibt (Stichwort: yield). Jede Funktion, die yield enthält, ist eine Generatorfunktion.

Wenn eine Generatorfunktion aufgerufen wird, wird ein Objekt zurückgegeben, über das iteriert werden kann. Wenn Sie über dieses Objekt iterieren (zum Beispiel, per foreach-Schleife), wird PHP die Iteratorfunktionen des Objekts jedes Mal aufrufen, wenn ein Wert benötigt wird. Dann wird der Status des Generators gesichert, so dass fortgefahren werden kann, wenn der nächste Wert benötigt wird.

Sobald keine weiteren Werte zurückgegeben werden können, kann der Generator einfach beendet werden, und der rufende Code wird fortgesetzt, als gäbe es keine weiteren Werte in einem Array.

Hinweis:

Ein Generator kann Werte zurückgeben, die unter Verwendung von Generator::getReturn() ermittelt werden können.

yield-Schlüsselwort

Das Herz einer Generatorfunktion ist das yield-Schlüsselwort. In seiner einfachsten Form sieht das yield-Schlüsselwort wie eine return-Anweisung aus, ausser dass die Ausführung mit der Rückgabe nicht beendet wird, sondern yield stattdessen bei der Schleife über den Generator einen Wert für den Code bereitstellt und die Ausführung der Generatorfunktion anhält.

Beispiel #1 Ein einfaches Beispiel zum liefern (yielding) von Werten

<?php
function generiere_eins_bis_drei() {
    for (
$i 1$i <= 3$i++) {
        
// Hinweis: $i bleibt zwischen den yields erhalten.
        
yield $i;
    }
}

$generator generiere_eins_bis_drei();
foreach (
$generator as $wert) {
    echo 
"$wert\n";
}
?>

Das oben gezeigte Beispiel erzeugt folgende Ausgabe:

1
2
3

Hinweis:

Intern werden sequentielle Integer-Schlüssel mit den abgelieferten Werten verknüpft, so wie mit einem nicht-assoziativen Array.

Achtung

Der Wert, der $daten zugewiesen wird, ist der Wert, der an Generator::send() übergeben wurde, oder null, wenn statt dessen Generator::next() aufgerufen wurde.

Produzieren von Werten mit Schlüsseln

PHP unterstützt ebenfalls assoziative Arrays, und Generatoren unterscheiden sich nicht davon. Als Ergänzung zum Produzieren einfacher Werte, wie oben gezeigt, können Sie zur gleichen Zeit auch einen Schlüssel liefern.

Die Syntax für das Produzieren eines Schlüssel/Wert-Paares ist sehr ähnlich wie die Definition von assoziativen Arrays, wie unten gezeigt.

Beispiel #2 Produzieren eines Schlüssel/Wert-Paares

<?php
/*
 * Die Eingabe sind Semikolon getrennte Felder, wobei das erste Feld
 * eine ID ist, die als Schlüssel genutzt wird.
 */

$eingabe = <<<'EOF'
1;PHP;mag Dollarzeichen
2;Python;mag Leerzeichen
3;Ruby;mag Blöcke
EOF;

function 
eingabe_parser($eingabe) {
    foreach (
explode("\n"$eingabe) as $zeile) {
        
$felder explode(';'$zeile);
        
$id array_shift($felder);

        yield 
$id => $felder;
    }
}

foreach (
eingabe_parser($eingabe) as $id => $felder) {
    echo 
"$id:\n";
    echo 
"    $felder[0]\n";
    echo 
"    $felder[1]\n";
}
?>

Das oben gezeigte Beispiel erzeugt folgende Ausgabe:

1:
    PHP
    mag Dollarzeichen
2:
    Python
    mag Leerzeichen
3:
    Ruby
    mag Blöcke
Achtung

Wie oben mit dem Zurückgeben einfacher Werte gezeigt, muss man beim Produzieren eines Schlüssel/Wert-Paares im Zuweisungskontext den yield-Befehl einklammern:

$daten = (yield $schluessel => $wert);

Produzieren von null-Werten

Yield kann ohne Argument aufgerufen werden, um einen null-Wert mit einem automatischen Schlüssel zurückzugeben.

Beispiel #3 Produzieren von nulls

<?php
function generiere_drei_nulls() {
    foreach (
range(13) as $i) {
        yield;
    }
}

var_dump(iterator_to_array(generiere_drei_nulls()));
?>

Das oben gezeigte Beispiel erzeugt folgende Ausgabe:

array(3) {
  [0]=>
  NULL
  [1]=>
  NULL
  [2]=>
  NULL
}

Produzieren als Referenz

Generatorfunktionen sind genauso in der Lage Werte als Referenz zurückzugeben, wie als Wert. Dies kann in gleicher Weise erfolgen, wie beim Zurückgeben von Referenzen aus Funktionen: dies geschieht, indem dem Funktionsnamen ein Kaufmanns-Und vorangestellt wird.

Beispiel #4 Produzieren von Werten als Referenz

<?php
function &generiere_referenz() {
    
$wert 3;

    while (
$wert 0) {
        yield 
$wert;
    }
}

/*
 * Hinweis: wir können $nummer innerhalb der Schleife ändern,
 * und weil der Generator Referenzen zurückgibt, wird $wert
 * innerhalb von generiere_referenz() verändert.
 */
foreach (generiere_referenz() as &$nummer) {
    echo (--
$nummer).'... ';
}
?>

Das oben gezeigte Beispiel erzeugt folgende Ausgabe:

2... 1... 0... 

Generatordelegation per yield from

Die Generatordelegation ermöglicht, mittels yield from-Ausdruck Werte von einem anderen Generator, Traversable-Objekt oder Array liefern zu lassen. Der äußere Generator liefert dann alle Werte vom inneren Generator, Objekt oder Array, bis dies nicht mehr gültig ist und die Ausführung im äußeren Generator fortfährt.

Falls ein Generator mit yield from verwendet wird, gibt der yield from-Ausdruck auch alle Werte zurück, die vom inneren Generator zurückgegeben werden.

Achtung

Speichern in ein Array (z.B. mit iterator_to_array())

yield from setzt nicht die Schlüssel zurück. Es erhält die Schlüssel, die vom Traversable-Objekt oder Array zurückgegeben wurden. Daher können einige Werte den selben Schlüssel mit einem anderen yield oder yield from gemein haben, der, bei der Einfügung in ein Array, vorherige Werte mit diesem Schlüssel überschreibt.

Ein üblicher Fall, für den dies relevant ist, ist iterator_to_array(), das standardmäßig ein indexiertes Array zurück gibt, was zu möglicherweise unerwarteten Ergebnissen führen kann. iterator_to_array() hat einen zweiten Parameter use_keys, der auf false gesetzt werden kann, um alle Werte zu sammeln, während die Schlüssel, die vom Generator geliefert werden, ignoriert werden.

Beispiel #5 yield from mit iterator_to_array()

<?php
function inner() {
    yield 
1// Schlüssel 0
    
yield 2// Schlüssel 1
    
yield 3// Schlüssel 2
}
function 
gen() {
    yield 
0// Schlüssel 0
    
yield from inner(); // Schlüssel 0-2
    
yield 4// Schlüssel 1
}
// Übergib false als zweiten Parameter, um das Array [0, 1, 2, 3, 4] zu erhalten
var_dump(iterator_to_array(gen()));
?>

Das oben gezeigte Beispiel erzeugt folgende Ausgabe:

array(3) {
  [0]=>
  int(1)
  [1]=>
  int(4)
  [2]=>
  int(3)
}

Beispiel #6 Grundlegende Verwendung von yield from

<?php
function zaehle_bis_zehn() {
    yield 
1;
    yield 
2;
    yield from [
34];
    yield from new 
ArrayIterator([56]);
    yield from 
sieben_acht();
    yield 
9;
    yield 
10;
}

function 
sieben_acht() {
    yield 
7;
    yield from 
acht();
}

function 
acht() {
    yield 
8;
}

foreach (
zaehle_bis_zehn() as $zahl) {
    echo 
"$zahl ";
}
?>

Das oben gezeigte Beispiel erzeugt folgende Ausgabe:

1 2 3 4 5 6 7 8 9 10 

Beispiel #7 yield from und Rückgabewerte

<?php
function zaehle_bis_zehn() {
    yield 
1;
    yield 
2;
    yield from [
34];
    yield from new 
ArrayIterator([56]);
    yield from 
sieben_acht();
    return yield from 
neun_zehn();
}

function 
sieben_acht() {
    yield 
7;
    yield from 
acht();
}

function 
acht() {
    yield 
8;
}

function 
neun_zehn() {
    yield 
9;
    return 
10;
}

$gen zaehle_bis_zehn();
foreach (
$gen as $zahl) {
    echo 
"$zahl ";
}
echo 
$gen->getReturn();
?>

Das oben gezeigte Beispiel erzeugt folgende Ausgabe:

1 2 3 4 5 6 7 8 9 10

Hier Kannst Du einen Kommentar verfassen


Bitte gib mindestens 10 Zeichen ein.
Wird geladen... Bitte warte.
* Pflichtangabe
Es sind noch keine Kommentare vorhanden.

Neuigkeiten für PHP-Entwickler: Laravel 11 Veröffentlichung

Am 12. März 2024 wurde die lang erwartete Version 11 des Laravel-Frameworks veröffentlicht, die eine Reihe von spannenden Neuerungen und Verbesserungen für die PHP-Entwicklungsgemeinschaft mit sich bringt. ...

Mike94

Autor : Mike94
Kategorie: PHP Magazin

Technisches SEO bleibt relevant

Technisches SEO – Was ist das überhaupt? Technisches SEO bezieht sich auf die Optimierung der technischen Aspekte deiner Webseite. Das Ziel ist klar! ...

admin

Autor : admin
Kategorie: SEO & Online-Marketing

Was ist neu in der PHP 8.2.10

PHP 8.2.10 ist eine der neuesten Versionen von PHP, die eine Reihe von Verbesserungen und neuen Funktionen mit sich bringt. In diesem Artikel werden wir einige der herausragenden Neuerungen und Verbesserungen dieser Version diskutieren. ...

admin

Autor : admin
Kategorie: Software-Updates

Tutorial veröffentlichen

Tutorial veröffentlichen

Teile Dein Wissen mit anderen Entwicklern weltweit

Du bist Profi in deinem Bereich und möchtest dein Wissen teilen, dann melde dich jetzt an und teile es mit unserer PHP-Community

mehr erfahren

Tutorial veröffentlichen

Seltsames Verhalten von execute() oder Fehler meinerseits

Hallo liebe Community, ich habe ein kleines Problem und vielleicht kann mir ja jemand helfen, würde ich mich sehr drüber freuen. Unten steht e ...

Geschrieben von garibaldiwz am 22.03.2024 13:03:12
Forum: SQL / Datenbanken
Google reCAPTCHA in Kontaktformular einbinden

Überprüfen Sie den E-Mail-Versand: Stellen Sie sicher, dass die E-Mail-Funktion mail() ordnungsgemäß funktioniert und dass keine Fehler beim V ...

Geschrieben von Gast am 18.03.2024 04:54:16
Forum: PHP Developer Forum
`count.php`

Hallo cober93327, und Danke fuer deine Antwort! :-) Naja, so einen "Besucherzähler" auf der Webseite anzuzeigen ist schon eher etwas, das man a ...

Geschrieben von kekse1 am 17.03.2024 15:56:38
Forum: Projekthilfe
`count.php`

Es gibt dazu natuerlich auch eine recht ausfuehrliche Dokumentation in meinem GitHub-Repository Es würde meiner Ansicht nach enorm helfen, wenn D ...

Geschrieben von cober93327 am 14.03.2024 15:49:28
Forum: Projekthilfe