package main
import (
"runtime"
"sync"
)
func main() {
runtime.GOMAXPROCS(1)
var wg sync.WaitGroup
wg.Add(20)
for i := 0; i < 10; i++ {
go func(i int) {
println(i)
wg.Done()
}(i)
}
for i := 10; i < 20; i++ {
go func(i int) {
println(i)
wg.Done()
}(i)
}
wg.Wait()
}
https://play.golang.org/p/nrEveScSaeI
问题: 执行结果为什么会先打印出 19 再顺序输出?请各位大佬不吝赐教
我记得之前有看过 M P G 模型中 GOMAXPROCS 可以控制 P 的数量
1
reus 2019-04-17 16:26:22 +08:00
偶然而已,按什么顺序都是对的,goroutine 的执行顺序是不确定的
|
3
keepeye 2019-04-17 16:30:14 +08:00
不专业的回答:最后一个 goroutine 会被放在一个"即将被执行的"地方,优先级最高。
话说,goroutine 不需要关心顺序吧 |
4
mscb 2019-04-17 16:31:45 +08:00 via Android
没仔细了解过细节。设置 gomaxprocs 后,应该只是控制 p 的数量,没有控制 m 的数量吧? m 不变的话底层还是会有多个线程,一个 g 阻塞了,其他 m 会来偷 g 过去运行。不知道我理解的对不对。欢以上仅供参考,欢迎各位大佬赐教,确实没仔细了解过调度这一块
|
5
punyGod 2019-04-17 16:33:18 +08:00
它会把最新的一个放到本地的 queue 中。这样它就会被优先执行
|
6
mscb 2019-04-17 16:35:56 +08:00 via Android
另外就算是单线程的协程也不能保证能顺序执行哇。主要看添加到队列里的形态,以及调度的情况
|
10
reus 2019-04-17 16:42:37 +08:00 1
@Fitz 讨论这种未定义行为没有任何意义,开了竞态检测,顺序就可能不同。不同版本的调度器也有可能不同,不同的编译器实现的运行时也可能不同。所以这就是偶然的行为,你的程序是不可以依赖这种未定义行为的。
|