关于 all goroutines are asleep 的问题

第一次见到这个错误,也是比较懵逼,如果自己搞不清这个问题为什么出现其实就是基本概念没理解清楚。下面我就说说这个问题。

其实这个问题很简单,就是根据字面就可以解释,所有的 groutine 睡着了。说白了就是产生了死锁,而且是所有的goruntine(用户级别的)都发生了死锁。如下代码会报此错误


package main

import (

"fmt"

"sync"

"time"

)

var a = sync.Mutex{}

var b = sync.Mutex{}

func main() {

a.Lock()

go block()

time.Sleep(time.Second)

b.Lock()

fmt.Println("main")

}

func block() {

b.Lock()

a.Lock()

fmt.Println("block")

}

以上代码,是两个goruntine 死锁,相当于两个goruntine都在等待对方,因此就出错了。但是如果单纯的理解为死锁也是不对的,因为在golang中不只死锁会引起此问题,看如下例子

package main

import "fmt"

func main() {
    package main

func main() {
    var a = make(chan int)
    a <- 1
    _ = <-a
}

这个例子是不是很神奇,先给 a 发送一个1,然后在接收就出问题了,这是为什么呢?我想应该很多没遇到这个问题的时候是想不明白的,这是因为 a <- 1 这个操作,是阻塞操作,就是说 遇到了 a<-1 代码就不走了,什么时候代码往下走?必须等到a里面的消息被读出去才会继续走,这个就不是锁引起的,所以单纯的理解为锁也是不对的。其实 alseep 才是最准确的描述方法,泛指引起goroutine挂起而且永远不会被唤醒的情况。

知道了产生错误的原因其实就很容易避免了,做法无非就是想清楚逻辑,因为正确的逻辑是不会出现这种情况的,出现了问题就根据报错的地方,看一下就知道怎么回事了,前提是你理解了产生问题的原因

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • Android 自定义View的各种姿势1 Activity的显示之ViewRootImpl详解 Activity...
    passiontim阅读 173,786评论 25 709
  • -无心施舍,是最高境界,你施舍乞丐,会高兴得意吗?就是你做好事的适合,心是平静的,没有得意或失落 -轻喜? -恩,...
    Leona2028阅读 314评论 0 0
  • 江湖风云出我辈,一入江湖岁月催。 雄图霸业谈笑中,不胜人间一场醉。 同样的一部《葵花宝典》,有人豁然的挥刀自宫,练...
    丁冬笔记阅读 394评论 0 0
  • 在iOS中和远程控制事件有关的只有一个- (void)remoteControlReceivedWithEvent...
    FallPine阅读 736评论 0 0
  • 写文章,我们通常会想好, 我们要向读者传达什么理念。明确目标后,我们利用已有的阅历和观点,佐证我们的理念...
    望书山阅读 1,331评论 9 3