- r - 以节省内存的方式增长 data.frame
- ruby-on-rails - ruby/ruby on rails 内存泄漏检测
- android - 无法解析导入android.support.v7.app
- UNIX 域套接字与共享内存(映射文件)
我正在尝试理解 Golang 中的一个 typical data races从多个 goroutines 访问未 protected 全局变量可能会导致竞争条件:
var service map[string]net.Addr
func RegisterService(name string, addr net.Addr) {
service[name] = addr
}
func LookupService(name string) net.Addr {
return service[name]
}
它继续说我们可以通过用互斥体保护它来解决这个问题:
var (
service map[string]net.Addr
serviceMu sync.Mutex
)
func RegisterService(name string, addr net.Addr) {
serviceMu.Lock()
defer serviceMu.Unlock()
service[name] = addr
}
func LookupService(name string) net.Addr {
serviceMu.Lock()
defer serviceMu.Unlock()
return service[name]
}
到目前为止,还不错。令我困惑的是:
this question 的公认答案这表明一个 CPU 绑定(bind)的 goroutine 会饿死其他已经被多路复用到同一个操作系统线程上的 goroutine(除非我们明确地让步 runtime.Gosched()
)。这是有道理的。
对我来说,上面的 RegisterService()
和 LookupService()
函数看起来受 CPU 限制,因为没有 IO 也没有 yield 。这是正确的吗?
如果是,并且如果 GOMAXPROCS 设置为 1,那么上例中的互斥体是否仍然是绝对必要的? goroutines 在可能出现竞争条件的地方受 CPU 限制这一事实不能解决这个问题吗?
即使是这样,我认为在现实生活中使用互斥量仍然是一个好主意,因为我们可能无法保证 GOMAXPROCS 的设置。还有其他原因吗?
最佳答案
正如 FUZxxl 和 Nick Craig-Wood 指出的,goroutines 的当前行为是特定于实现的。所以,也许,读取或写入 map 可以产生。考虑到 maps are not thread safe 、互斥或其他同步是正确的并发访问所必需的。
作为互斥体的替代方案,您可以生成一个 goroutine,它在您的 map 上执行所有操作并通过 channel 与其对话:
type writereq struct {
key string
value net.Addr
reply chan struct{}
}
type readreq struct {
key string
reply chan net.Addr
}
var service map[string]net.Addr
var reads = make(chan readreq)
var writes = make(chan writereq)
func RegisterService(name string, addr net.Addr) {
w := writereq{name, addr, make(chan struct{})}
writes <- w
return <-w.reply // return after registration confirmation
}
func LookupService(name string) net.Addr {
r := readreq{name, make(chan net.Addr)}
reads <- r
return <-r.reply
}
func serveRegistry() {
for {
select {
case r := <-reads:
r.reply <- service[r.name]
case w := <-writes:
service[w.name] = w.addr
w.reply <- struct{}
}
}
}
关于go - GOMAXPROCS=1 时的数据竞争,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19066478/
我很好奇 Go 运行时如何确定 runtime.NumCPU()(CPU 数)在具有截然不同特性的各种平台(如 Linux、macOS 和 Windows)上? 例如在 Linux 上:我很好奇它是否
不设置同名环境变量时,是否保证GOMAXPROCS设置为1? 此代码显示值: package main import ( "runtime" "fmt" ) func getGOMAX
我有一个简单的 go 程序 - main.go - package main import ( "log" "runtime" "time" ) func main() {
我试图在主线程中同时运行一个 goroutine(go 版本 go1.4.1 darwin/amd64)和无限循环,但我无法让它工作。如果我理解正确的话,如果我指定了 GOMAXPROCS,go 应该
我们都知道runtime.GOMAXPROCS默认设置为CPU核心数,如果这个属性设置的太大了怎么办? 程序会有更多上下文切换吗? 是否会更频繁地触发垃圾收集器? 最佳答案 GOMAXPROCS 默认
我已经设置了 runtime.GOMAXPROCS(2),但是这个程序在输出一些数字时仍然挂起。我可以看到这个程序使用了高 cpu(超过 100%),但我不明白为什么 for 循环 goroutine
我在 MacBook 和 Ubuntu 上玩 golang 1.7.3,发现 runtime.GOMAXPROCS 被限制为 256。有人知道这个限制是从哪里来的吗?这是否记录在任何地方,为什么会有限
我见过有人将 runtime.GOMAXPROCS 设置为 runtime.NumCPU() 以启用并行 处理去。 Official documentation没有说明 GOMAXPROCS 的上限;
我正在尝试理解 Golang 中的一个 typical data races从多个 goroutines 访问未 protected 全局变量可能会导致竞争条件: var service map[st
在下面的 GoLang 程序中,我试图实现 stable marriage problem对于 N 个男人和 N 个女人,使用 2*N 个协程(每个男人和女人 1 个)。 程序严格遵循程序定义,因为每
The GOMAXPROCS variable limits the number of operating system threads that can execute user-level Go
对不起,如果这听起来很愚蠢。 如果在 runtime.NumCpu() == 2 时运行 runtime.GOMAXPROCS(4) 会发生什么? 最佳答案 runtime.GOMAXPROCS 控制
我正在玩 Go,在我的 2015 8 核 MacBookPro 上运行 go 1.7.3。 尝试了解 runtime.GOMAXPROCS 设置为其最大值 (256) 并启动相同数量的 gorouti
我只是想试试goroutine切换上下文的速度有多快,所以写了下面的代码。令我惊讶的是,多个 gorountines 比不需要切换上下文的版本运行得更快(我将程序设置为仅在一个 CPU 内核中运行)。
我是一名优秀的程序员,十分优秀!