您的位置 首页 知识分享

GO:缺乏同步

var a string var done bool func setup() { a = "hel…

GO:缺乏同步

var a string var done bool  func setup() {     a = "hello, world"     done = true }  func doprint() {     if !done {         once.do(setup)     }     print(a) }  func twoprint() {     go doprint()     go doprint() } 
登录后复制

代码分析

变量:

  • a 和 b 是 int 类型的全局变量,为所有 goroutine 共享。

功能:

  • f():
    • 顺序写入 a 和 b(a = 1 且 b = 2)。
  • g():
  • 读取并打印 b,然后打印 a。

mn() 中的并发:

  • 函数 f() 使用 go f() 作为单独的 goroutine 执行。
  • 函数 g() 直接在主 goroutine 中执行。

潜在问题:

  • 运行 f() 的 goroutine 和执行 g() 的主 goroutine 并发运行。
  • 在 g() 读取并打印 a 和 b 的值之前,f() 中对 a 和 b 的写入可能无法完成。
  • 这引入了数据竞争,其中(在 f() 中写入并在 g() 中读取)发生在共享内存(a 和 b)上,而无需同步。

可能的结果
由于缺乏同步,程序的输出是不确定的。以下是可能的情况:

情况 1:g() 在 f() 修改 a 和 b 之前执行:

  • a 和 b 的初始值为 0(go 中未初始化 int 的默认值)。
0 0  
登录后复制

情况 2:如果 b = 2 在 g() 之前完成,但 a = 1 未完成,则输出可能为:

2 0 
登录后复制

主要观察结果
数据竞争:在不同步的情况下对 a 和 b 进行并发访问会引入数据竞争。这使得程序的行为变得不确定且不可预测

修复代码

  1. 使用sync.waitgroup: 确保 f() 在 g() 执行之前完成
var a, b int var wg sync.waitgroup  func f() {     a = 1     b = 2     wg.done() }  func g() {     print(b)     print(a) }  func main() {     wg.add(1)     go f()     wg.wait()     g() }  
登录后复制
  1. 使用频道: 当 f() 完成时发出信号:
var a, b int  func f(done chan bool) {     a = 1     b = 2     done <- true }  func g() {     print(b)     print(a) }  func main() {     done := make(chan bool)     go f(done)     <-done     g() }  
登录后复制

这里,g() 等待,直到 f() 通过完成的通道发送信号。

以上就是GO:缺乏同步的详细内容,更多请关注php中文网其它相关文章!

本文来自网络,不代表甲倪知识立场,转载请注明出处:http://www.spjiani.cn/wp/5685.html

作者: nijia

发表评论

您的电子邮箱地址不会被公开。

联系我们

联系我们

0898-88881688

在线咨询: QQ交谈

邮箱: email@wangzhan.com

工作时间:周一至周五,9:00-17:30,节假日休息

关注微信
微信扫一扫关注我们

微信扫一扫关注我们

关注微博
返回顶部