Goroutine执行我的函数所需的时间与for循环相同。

huangapple go评论82阅读模式
英文:

Goroutine is taking same time to execute my function as for loop

问题

我有一个用于创建Istio VirtualService对象的函数。
我正在使用goroutines并发地执行我的函数,启动100个工作线程。

            var data map[string]string
			for _, data = range MapList {
				wg.Add(1)
				limit.Execute(func() {
					go func(data map[string]string) {
						defer wg.Done()
						_,_ = m.createVirtualServices(ctx, data, namespace)
					}(data)
				})
				wg.Wait()
			}

如果我只是循环遍历MapList并执行我的函数,这将花费完全相同的时间。

为什么会这样?

英文:

I have a function to create Istio VirtualService objects.
I am using goroutines to execute my function concurrently, starting 100 workers.

            var data map[string]string
			for _, data = range MapList {
				wg.Add(1)
				limit.Execute(func() {
					go func(data map[string]string) {
						defer wg.Done()
						_,_ = m.createVirtualServices(ctx, data, namespace)
					}(data)
				})
				wg.Wait()
			}

this takes exact same time to execute if I'd just loop over seMapList and execute my function.

Why?

答案1

得分: 4

因为你在启动 goroutine 后立即等待它完成。请尝试使用以下代码替代:

for _, data := range MapList {
    wg.Add(1)
    limit.Execute(func() {
        go func(data map[string]string) {
            defer wg.Done()
            _, _ = m.createVirtualServices(ctx, data, namespace)
        }(data)
    })
}
wg.Wait() // 在所有 goroutine 创建完成后等待它们完成

这段代码会在创建所有 goroutine 后等待它们完成。

英文:

Because you are waiting for the goroutine to complete right after you start it. Try this instead:

            for _, data = range MapList {
                wg.Add(1)
                limit.Execute(func() {
                    go func(data map[string]string) {
                        defer wg.Done()
                        _,_ = m.createVirtualServices(ctx, data, namespace)
                    }(data)
                })
            }
            wg.Wait() // Wait for them after all goroutines are created

答案2

得分: 1

@Burak Serdan的答案是正确的,但可能不适用于这种情况。从我看到的情况来看,您将匿名函数传递给limit.Execute,因此您的匿名函数将确实启动新的goroutine,但不是立即启动,而是在limit.Execute在某个地方调用此匿名函数之后。

但是,您可以传递一个函数,该函数将运行N个goroutine。

var data map[string]string

limit.Execute(func() {
	for _, data = range MapList {
		wg.Add(1)
		go func(data map[string]string) {
			defer wg.Done()
			_,_ = m.createVirtualServices(ctx, data, namespace)
		}(data)
	}
})
wg.Wait()
英文:

@Burak Serdan answer is right but probably not in this case. From what I see you pass annonymous function to limit.Execute so your annonymous function will really start new goroutine but not immediatelly but after limit.Execute will call this annonymous function somewhere inside.

But instead of passing N annonymous functions you can pass one function which will then fun N goroutines

var data map[string]string

limit.Execute(func() {
	for _, data = range MapList {
		wg.Add(1)
		go func(data map[string]string) {
			defer wg.Done()
			_,_ = m.createVirtualServices(ctx, data, namespace)
		}(data)
	}
})
wg.Wait()

huangapple
  • 本文由 发表于 2021年9月28日 02:54:25
  • 转载请务必保留本文链接:https://go.coder-hub.com/69351916.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定