Go в примери: Чакални

За да изчакаме множество гозадачи да свършат работа, можем да ползваме чакалня.

package main
import (
    "fmt"
    "sync"
    "time"
)

Това е функцията, която ще изпълним във всяка гозадача.

func работник(id int) {
    fmt.Printf("Работник %d започва работа.\n", id)

Заспиваме, за да наподобим тежка задача.

    time.Sleep(time.Second)
    fmt.Printf("Работник %d е готов.\n", id)
}
func main() {

Тази чакалня – структура от вида sync.WaitGroup – ще ползваме, за да чакаме всички пуснати гозадачи да свършат работа. Забележка: Ако ще подавате чакалня на функция трябва да подадете указател към нея.

    var wg sync.WaitGroup

пускаме няколко гозадачи с помощта на WaitGroup.Go.

    for i := 1; i <= 5; i++ {
        wg.Go(func() {
            работник(i)
        })
    }

Спираме програмата, докато всички гозадачи, пуснати от wg станат готови. Гозадачата е готова, когато функцията, която тя извиква, се изпълни.

    wg.Wait()

Забележте, че при този подход няма ясен начин как да предадем вероятните грешки от работниците. За по-сложни случаи може да ползвате пакета errgroup.

}
$ go run waitgroups.go
Работник 5 започва работа.
Работник 3 започва работа.
Работник 4 започва работа.
Работник 2 започва работа.
Работник 1 започва работа.
Работник 4 е готов.
Работник 3 е готов.
Работник 5 е готов.
Работник 2 е готов.
Работник 1 е готов.

Редът на тръгващи и спиращи работници може да е различен при всяко пускане.

Следващ пример: .