【发布时间】:2022-10-08 05:58:22
【问题描述】:
我继承了一些我仍在尝试理解的代码。它的核心是这样的:
for msg := range this.out {
for i, handler := range this.handlers {
select {
case handler <- msg:
default:
this.logger.Printf("Buffer overflow occurred for handler %s", this.names[i])
}
}
}
出是chan byte
处理程序是[]chan []byte
它看起来像这样从数组中读取并写入处理程序,默认是抱怨缓冲区溢出。我认为。
但我需要细节。我是新手,这是我第一次与陈打交道。所以第一个问题,这真的是这里发生的事情吗?如果是这样......我如何防止缓冲区溢出?
【问题讨论】:
-
在我看来,这是从
out读取msg,然后尝试将msg写入全部handlers数组中的频道。但是,如果handlers中的任何通道当前有一个完整的缓冲区(或者是一个未准备好接收消息的无缓冲通道)而不是写入该特定通道,则会记录溢出消息。这就是代码的作用,尽管不知道编写此代码的原因,我们无法告诉您原因。 -
它不会与处理程序一起编译是
[]chan []byte。试着给一个minimal-reproducible-example去操场链接:go.dev/play/p/UVDicgckQe- -
对我来说,这段代码意味着每个
handler频道接收消息并不重要。可能是有意的,通道可能已满,而没有传递更多消息。确保真正的错误是使用听起来吓人的“缓冲区溢出”短语而不是“退避客户端 %s,它已经落后太远了,以后必须查询丢失的消息”。在不了解用例的情况下,不可能说,但该代码对我来说是可疑的。 Woody 的“使用渠道作为基础设施”这句话让我产生了共鸣。 -
它确实编译。如果这有什么不同的话,go 版本是“go1.13.15 linux/amd64”。我能做些什么来确保处理程序跟上。 tbh 我什至看不到处理程序在做什么。几乎可以肯定是因为我不熟悉 go 频道的工作原理。设置它的代码如下:
-
` port := mqPort out := make (chan []byte, bufsize) dist.Subscribe("mq:"+mqPort, out) ` ... 其中 Subscribe 是: ` func (this *Dist) Subscribe(name string, handler chan []byte) { this.names = append(this.names, name) this.handlers = append(this.handlers.handler) } `所以处理程序是由 make() 调用创建的“out”并传递给 Subscribe() ...但它要去哪里?看起来它是一个无处可去的通道,只有一个给定大小的缓冲区被填满。我没有看到任何建立做任何添加到该缓冲区的任何内容。
标签: go channel buffer-overflow