Heim  >  Artikel  >  Backend-Entwicklung  >  Detaillierte Einführung in den PHP-Generator

Detaillierte Einführung in den PHP-Generator

小云云
小云云Original
2018-03-06 13:09:452783Durchsuche

Schauen wir uns zunächst an, wie es in der offiziellen PHP-Dokumentation eingeführt wird: Generatoren bieten eine einfachere Möglichkeit, einfache Objektiterationen zu implementieren, verglichen mit der Art und Weise, eine Klasse zur Implementierung der Iterator-Schnittstelle zu definieren und Komplexität werden stark reduziert.

Nachdem wir diesen Satz gelesen haben, können wir mehrere Schlüsselwörter erhalten: Objektiteration, Iterator-Schnittstelle, Leistungsaufwand, relativ abstrakt, Reden ist billig, zeigen Sie mir den Code, beginnen wir mit dem klassischsten Beispiel eines Generators. Fangen wir an .

Die Funktion range() in PHP erstellt ein Array mit der angegebenen Bereichseinheit im Speicher und gibt es bei Verwendung zurück. Im Allgemeinen ist daran nichts auszusetzen, aber wenn der übergebene Grenzwertparameter eingegeben wird Es ist sehr groß, was bedeutet, dass das Array, das im Speicher erstellt wird, auch sehr groß ist. Dies ist der Rhythmus, der den Speicher platzt. An dieser Stelle können wir den Generator verwenden, um eine effizientere Range-Funktion zu implementieren (der folgende Code ist eine vereinfachte Version der offiziellen PHP-Dokumentation):

function xrange($start, $limit, $step = 1)
{
    //校验参数,此处省略

    for ($i = $start; $i <= $limit; $i += $step) {
        //向外产出值
        yield $i;
    }
}

//xrange此时返回的是一个生成器对象
$gen = xrange(1, 9);

//对生成器进行迭代
foreach ($gen as $number) {
    echo "$number ";
}

Die xrange- und range-Funktionen haben hier den gleichen Effekt. , beide generieren eine iterierbare Variable, aber der Unterschied besteht darin, dass die Range-Funktion ein bisschen dem ähnelt, was in ORM oft als „Vorladen“ bezeichnet wird, während xrange „Lazy Loading“ ist und nur wartet, bis die Iteration diesen Punkt erreicht, um den entsprechenden Wert zu generieren Daher ist xrange nicht erforderlich. Es ist nicht erforderlich, große Speicherblöcke zum Speichern von Variablen zuzuweisen, was erheblich Speicher spart und die Effizienz verbessert.

Lassen Sie uns nun die Ähnlichkeiten und Unterschiede zwischen Generatoren und gewöhnlichen Funktionen zusammenfassen:

  1. Der Generator muss das Schlüsselwort yield enthalten (wird zum Generieren von Ergebnissen verwendet) und kann in vielen Fällen vorkommen Sie können „return“ nur verwenden, um in normalen Funktionen Ergebnisse nach außen zurückzugeben, und die Funktion wurde ausgeführt Kompilierungsfehler. Schwerwiegender PHP-Fehler: Generatoren können keine Werte mit „return“ zurückgeben (Hinweis: Dies wird unter PHP7 nicht schief gehen, aber der Generator wird beendet und die Ausführung fortgesetzt. Das heißt, der Aufruf der valid()-Methode führt zu einer Rückgabe false. In PHP5 ist return empty jedoch eine gültige Syntax und beendet den Generator und setzt die Ausführung fort)

  2. Generator-Klasse (Generator)

  3. Generator-Objekt wird zurückgegeben vom Generator, $gen im obigen Code Es ist nur ein Generatorobjekt. Beachten Sie, dass sich das Generatorobjekt von Objekten anderer Klassen unterscheidet. Es kann nicht über das Schlüsselwort new erstellt werden, sondern kann nur über die Generatorfunktion abgerufen werden. Schauen wir uns zunächst die Zusammenfassung der Generator-Klasse an, um deren Zusammensetzung zu sehen:

Aus der obigen Klassenzusammenfassung können wir ersehen, dass die Generator-Klasse die Iterator-Schnittstelle implementiert, also die Eigenschaften einer hat Iterator. Darüber hinaus werden die Methoden send(), throw() und __wekeup() hinzugefügt. Die entsprechenden Methodenbeschreibungen wurden kommentiert und werden hier nicht wiederholt.

Ich habe viel geschrieben und festgestellt, dass mein Schreiben nicht gut ist, also könnte ich genauso gut ein Bild zeichnen, um ein Gefühl dafür zu bekommen (die Bilder sind auch nicht schön, also begnüge dich einfach damit, 2333)
Generator implements Iterator
{
    /**
     * 返回当前产生的值(yield后面表达式的值)
     */
    public mixed current ( void )

    /**
     * yield的键(yield &#39;key&#39;=>&#39;val&#39;;)
     */
    public mixed key ( void )

    /**
     * 从上一个yield之后继续执行,直到下一个yield
     */
    public void next ( void )

    /**
     * 重置迭代器(对于生成器并没什么卵用)
     */
    public void rewind ( void )

    /**
     * 向生成器中传入一个值,并从上一个yield之后继续执行
     */
    public mixed send ( mixed $value )

    /**
     * 向生成器中抛出一个异常,并从上一个yield之后继续执行
     */
    public void throw ( Exception $exception )

    /**
     * 检查迭代器是否被关闭(false表示已关闭)
     */
    public bool valid ( void )

    /**
     * 序列化回调,但是生成器不能被序列化,因此会抛出一个异常
     */
    public void __wakeup ( void )
}

Yield-Schlüsselwörter


Als nächstes werfen wir einen Blick auf das Yield-Schlüsselwort. Seine einfachste Aufrufform sieht aus wie die Rückgabe einer normalen Funktion. Der Unterschied besteht darin, dass eine normale Rückgabe a zurückgibt value und beendet die Ausführung der Funktion, während yield einen Wert an den Code zurückgibt, der diesen Generator durchläuft und einfach die Ausführung der Generatorfunktion anhält.

Dies ist ein typischer Yield-Ausdruck: $data = yield $key => $value; Dieser Ausdruck besteht aus zwei Teilen:

Hinweis: PHP5 erfordert Klammern $data = (yiel

d $key => $value);, andernfalls tritt ein Kompilierungsfehler auf, PHP7 muss sich nicht darum kümmern

<br/>
Einer ist der Ausdruck nach yield Ausdruck, dieser kann ein einzelner sein Wert oder ein Schlüssel-Wert-Paar, das einem Element im Array entspricht, wird an den Aufruf der oberen Ebene zurückgegeben, dh die obere Ebene kann den Wert über die aktuelle Methode empfangen oder die Rückgabe des Sendens ausführen Methode.
  • Der andere Teil ist das yield-Schlüsselwort selbst, das den von der send-Methode übergebenen Wert erhält Wert des gesamten Ertragsausdrucks Der Wert kann von der Variablen auf der linken Seite empfangen werden.

  • Das mag etwas abstrakt sein, aber schauen wir uns das Bild oben an:

Generator-Delegierter (Ertrag von)


PHP7 hat Mit dem hinzugefügten Schlüsselwort yield From ermöglicht diese Syntax die Ausgabe von Werten von anderen Generatoren, durchlaufbaren Objekten oder Arrays über die Funktion yield from generation. Die verschiedenen Merkmale von yield from sind dieselben wie yield, das Daten generiert, die folgenden Ausdrücke sind jedoch unterschiedlich. Schauen wir uns ein Beispiel an (Auszug aus der offiziellen PHP-Dokumentation):

function count_to_ten()
{
    yield 1;
    yield 2;
    yield from [3, 4];  //生成数组
    yield from new ArrayIterator([5, 6]);   //生成可遍历对象
    yield from seven_eight();   //生成生成器对象
    yield 9;
    yield 10;
}

function seven_eight()
{
    yield 7;
    yield from eight();
}

function eight()
{
    yield 8;
}

foreach (count_to_ten() as $num) {
    echo "$num ";
}

//输出:1 2 3 4 5 6 7 8 9 10

yield from以方便我们编写比较清晰生成器嵌套,这点可以类比于函数中的嵌套调用,当函数A中调用另一个函数B,此时会等B执行完成并返回,方才继续执行。在没有yield from的时候,实现生成器嵌套需要自己实现栈并进行压栈和弹出操作以达到相同效果,那是多么痛苦的操作。

相关推荐:

php生成器简介和示例

php生成器对象

PHP生成器简单实例,php生成器_PHP教程

Das obige ist der detaillierte Inhalt vonDetaillierte Einführung in den PHP-Generator. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Stellungnahme:
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn