为什么 Go 例程会这样?

问题描述 投票:0回答:1

我正在读一本叫做《Go in action》的书,我对书中的 goroutine 部分感到有点困惑,基本上我想了解有关以下代码的两件事:

package main

import (
    "fmt"
    "runtime"
    "sync"
    "time"
)

var counter int = 0
var wg sync.WaitGroup
var mtx sync.Mutex

func main() {
    wg.Add(2)

    runtime.GOMAXPROCS(1)

    go incCounter("A")
    go incCounter("B")

    wg.Wait()
    fmt.Println(counter)
}

func incCounter(prefix string) {
    fmt.Println("Started thread ", prefix)
    defer wg.Done()
    mtx.Lock()
    {
        fmt.Println("Incrementing counter from ", prefix)
        counter = counter + 1
        fmt.Println("Passing to another thread")
        runtime.Gosched()
        for i := 1; i < 100; i++ {
            time.Sleep(1 * time.Second)
            fmt.Println("Thread still executing ", prefix)
        }
    }
    mtx.Unlock()
}

输出为:

Started thread  B
Incrementing counter from  B
Passing to another thread
Started thread  A
Thread still executing  B
Thread still executing  B
Thread still executing  B
Thread still executing  B
  1. 为什么它先执行goroutine B?因为在代码中 goroutine A 首先出现,所以我希望它也先运行。
  2. goroutine B 使用 .Gosched 方法让 goroutine A 开始执行,但由于互斥体被锁定,goroutine A 将等待解锁。此时我将GOMAXPROCS设置为只有一个逻辑处理器,为什么看起来两个goroutine是并行运行的呢?这真的应该发生吗?

正如我所言,将 gomaxprox 设置为 1 将允许一次只执行一个 goroutine,但在这种情况下,情况似乎并非如此,实际上两个 goroutine 都在并行运行。

multithreading go goroutine
1个回答
0
投票

Goroutines 并发运行。这意味着,如果有可用的处理器,调度程序可以安排它们并行运行。如果只有一个处理器可用,它们仍然会同时运行,但在任何给定时刻只有一个 goroutine 会运行。

Go 运行时不保证哪个 goroutine 将首先运行。因此一组新创建的 goroutine 的运行顺序将是随机的,

© www.soinside.com 2019 - 2024. All rights reserved.