Ich muss eine große Menge an Goroutines starten und auf ihre Beendigung warten. Der intuitive Weg scheint einen Kanal zu verwenden, um zu warten, bis alle fertig sind:
%Vor%Aber das Problem ist, dass sich die Anzahl der Objekte und damit auch die Menge der Goroutines ändern könnte. Ist es möglich, die Puffergröße eines Kanals zu ändern?
Gibt es vielleicht einen eleganteren Weg, dies zu tun?
Diese Aufgabe ist nicht gerade trivial, es ist ziemlich einfach, eine fehlerhafte zu schreiben. Ich empfehle, eine fertige Lösung in der stdlib zu verwenden - sync.WaitGroup
. Zitat aus dem Link:
Eine WaitGroup wartet auf das Ende einer Sammlung von Gatoruins. Die Hauptgoroutine ruft Add auf, um die Anzahl der wartenden Goroutinen festzulegen. Dann läuft jeder der Goroutinen und ruft Fertig, wenn fertig. Gleichzeitig kann Wait zum Blockieren verwendet werden, bis alle Goroutines beendet sind.
@tjameson hat einen tollen Job gemacht und erklärt, wie man WaitGroup
benutzt, wie man einen Verweis auf dein WaitGroup
Objekt an deine Funktion weitergibt. Die einzige Änderung, die ich an seinem Beispiel vornehmen würde, ist Leverage defer
, wenn Sie Done
sind. Ich denke, dass defer ws.Done()
sollte die erste Aussage in Ihrer Funktion sein.
Ich mag die Einfachheit von WaitGroup
. Allerdings mag ich nicht, dass wir den Verweis auf die Goroutine übergeben müssen, weil das bedeuten würde, dass die Parallelitätslogik mit Ihrer Geschäftslogik gemischt wäre.
Also habe ich diese generische Funktion entwickelt, um dieses Problem für mich zu lösen:
%Vor%So könnte Ihr Beispiel auf diese Weise gelöst werden:
%Vor%Wenn Sie es verwenden möchten, können Sie es hier Ссылка
findenTags und Links concurrency go channel goroutine coroutine