英文:
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()
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论