如何在 Golang 的并发代码中延迟工作
How working defer in concurrency code in Golang
我有一些代码:
...
func Run(tasks []Task, n, m int) error {
...
for i := 0; i < n; i++ {
go func() {
defer wg.Done()
for t := range taskCh {
if atomic.LoadInt32(&errCount) >= int32(m) {
return
}
if err := t(); err != nil {
atomic.AddInt32(&errCount, 1)
}
}
}()
}
for _, t := range tasks {
taskCh <- t
}
close(taskCh)
wg.Wait()
if atomic.LoadInt32(&errCount) >= int32(m) {
err = ErrErrorsLimitExceeded
}
...
}
它工作正常,但为什么在我编写操作 close() wg.Wait 和 if... 时它不起作用?
...
defer func() {
close(taskCh)
wg.Wait()
if atomic.LoadInt32(&errCount) >= int32(m) {
err = ErrErrorsLimitExceeded
}
}()
for i := 0; i < n; i++ {
...
当变量 errCount = 0
这是 golang 的限制,您不能从延迟函数更改 returned 变量。正确的做法是(注意(err error)
命名为return值):
package main
import "fmt"
func someFunction() (err error) {
defer func() {
err = fmt.Errorf("Some error")
}()
err = fmt.Errorf("Some other error")
return
}
func main() {
fmt.Println(someFunction())
}
我有一些代码:
...
func Run(tasks []Task, n, m int) error {
...
for i := 0; i < n; i++ {
go func() {
defer wg.Done()
for t := range taskCh {
if atomic.LoadInt32(&errCount) >= int32(m) {
return
}
if err := t(); err != nil {
atomic.AddInt32(&errCount, 1)
}
}
}()
}
for _, t := range tasks {
taskCh <- t
}
close(taskCh)
wg.Wait()
if atomic.LoadInt32(&errCount) >= int32(m) {
err = ErrErrorsLimitExceeded
}
...
}
它工作正常,但为什么在我编写操作 close() wg.Wait 和 if... 时它不起作用?
...
defer func() {
close(taskCh)
wg.Wait()
if atomic.LoadInt32(&errCount) >= int32(m) {
err = ErrErrorsLimitExceeded
}
}()
for i := 0; i < n; i++ {
...
当变量 errCount = 0
这是 golang 的限制,您不能从延迟函数更改 returned 变量。正确的做法是(注意(err error)
命名为return值):
package main
import "fmt"
func someFunction() (err error) {
defer func() {
err = fmt.Errorf("Some error")
}()
err = fmt.Errorf("Some other error")
return
}
func main() {
fmt.Println(someFunction())
}