gpt4 book ai didi

go - Go例程中的有限循环

转载 作者:IT王子 更新时间:2023-10-29 01:52:13 24 4
gpt4 key购买 nike

我正在尝试在完成该主题后同步执行两个或多个 go routine

goroutines order of execution

然后我写了一些代码来测试 go routines 的行为(我把它当作一个队列,顺便说一句,go 并发教程页面对我没有真正帮助)

package main

import (
"fmt"
"sync"
)

const size = 10
var vChan chan int = make(chan int, size)

func justSend(wg *sync.WaitGroup) {
defer wg.Done()
for i := 1; i <= 10; i++ {
vChan <- i
}
}

func justPrint(wg *sync.WaitGroup) {
defer wg.Done()
v := <- vChan
fmt.Printf("%4d ", v);
}

func main() {
wg := new(sync.WaitGroup)

go func() {
wg.Add(1)
go justSend(wg)
wg.Wait()
wg.Add(size)
go justPrint(wg)
wg.Wait()
close(vChan)
}()
}

但是它什么都不打印,我们应该设计一个 go 例程总是有一个无限循环,否则我们无法让它正常工作吗?

(这段代码是为我构建多个 websocket 连接和测试我们的 API 服务器响应的实际问题准备的,所以......我认为在不同函数之间传递一堆具有相同类型的 channel 非常烦人,所以我设置它在全局范围内)

最佳答案

不,不要使用无限循环。同步最好用 channel 或同步包的工具来完成。main() 也是一个goroutine(主要的),所以如果main 在其他 goroutines 之前退出,您的任务仍未完成。一种方法是使用 sync.WaitGroup 等待其他 goroutine 完成(参见示例 1、2 和 3)。另一种方法是使用 channel 等待其他 goroutine 完成(参见示例 4 和 5)。我提供了一些示例,因此您可以选择适合您情况的示例:


1- 一个 tx 和多个 rx(保持 channel 打开),尝试 this :

package main

import (
"fmt"
"sync"
)

func main() {
go tx()
wg.Add(20)
for i := 1; i <= 20; i++ {
go rx()
}
wg.Wait()
}

func tx() {
for i := 1; i <= 20; i++ {
vChan <- i
}
}

func rx() {
defer wg.Done()
fmt.Println(<-vChan)
}

var wg sync.WaitGroup

var vChan = make(chan int, 10)

2- 一个 tx 和一个 rx(保持 channel 打开),尝试 this :

package main

import (
"fmt"
"sync"
)

func main() {
go tx()
wg.Add(1)
go rx()
wg.Wait()
}

func tx() {
for i := 1; i <= 20; i++ {
vChan <- i
}
}

func rx() {
defer wg.Done()
for i := 1; i <= 20; i++ {
fmt.Println(<-vChan)
}
}

var wg sync.WaitGroup

var vChan = make(chan int, 10)

3- 关闭 channel 到 tx 的信号端,尝试 this :

package main

import (
"fmt"
"sync"
)

func main() {
go tx()
wg.Add(1)
go rx()
wg.Wait()
}

func tx() {
for i := 1; i <= 5; i++ {
vChan <- i
}
close(vChan)
}

func rx() {
defer wg.Done()
for v := range vChan {
fmt.Println(v)
}
}

var wg sync.WaitGroup

var vChan = make(chan int, 10)

4- 关闭 channel 到 tx 的信号端,使用主 goroutine 进行 rx,尝试 this :

package main

import (
"fmt"
)

func main() {
go tx()
for v := range vChan {
fmt.Println(v)
}
}

func tx() {
for i := 1; i <= 20; i++ {
vChan <- i
}
close(vChan)
}

var vChan = make(chan int, 10)

5- 使用退出 channel ,尝试 this :

package main

import (
"fmt"
)

func main() {
go tx()
go rx()
<-quit
}
func rx() {
for v := range vChan {
fmt.Println(v)
}
quit <- struct{}{}
}
func tx() {
for i := 10; i <= 15; i++ {
vChan <- i
}
close(vChan)
}

var quit = make(chan struct{}, 1)
var vChan = make(chan int, 10)

输出:

10
11
12
13
14
15

6- 多发送多接收,尝试 this :

package main

import (
"fmt"
"sync"
)

func main() {
wg.Add(5)
for i := 1; i <= 5; i++ {
go tx()
go rx()
}
wg.Wait()
}

var n = 10

func tx() {
vChan <- n
n++
}

func rx() {
defer wg.Done()
fmt.Println(<-vChan)
}

var wg sync.WaitGroup

var vChan = make(chan int, 10)

7- 多发一收,试试this :

package main

import (
"fmt"
"sync"
)

func main() {
for i := 1; i <= 5; i++ {
wg.Add(1)
go tx()
}

go rx()
wg.Wait()
}

func rx() {
for {
fmt.Println(<-vChan)
wg.Done()
}
}

var n = 20

func tx() {
vChan <- n
n++
}

var wg sync.WaitGroup

var vChan = make(chan int, 10)

希望对您有所帮助。

关于go - Go例程中的有限循环,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47257954/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com