为了账号安全,请及时绑定邮箱和手机立即绑定

有没有可靠的方法来确保 Go 通道在读取时不会阻塞?

有没有可靠的方法来确保 Go 通道在读取时不会阻塞?

Go
摇曳的蔷薇 2021-10-04 09:39:58
这是对上一个具有相似名称的线程的后续操作。它有一个公认的答案,但该答案并不能真正回答问题。从那个线程,这里是用例:if len(myChannel) > 0 {   // Possible issue here: length could have changed to 0 making this blocking   elm := <- myChannel   return elm }OP 称其为“可能的问题”,但它是一个确定的问题:一种竞争条件,其中另一个消费者可能从 if 条件的评估和两个语句的执行之间的通道中提取了一个值。现在,我们被告知 Go Way 更倾向于通道而不是互斥锁,但在这里,如果不将互斥锁和通道配对在一起,并使用我们新的并发数据类型而不是通道。可以吗?真的没有办法通过提前检查空间来可靠地确保 recv 不会阻塞吗?(与 Java 中的 BlockingQueue.poll() 或其他基于队列的消息传递 IPC 设施中的类似设施相比...)
查看完整描述

2 回答

?
ibeautiful

TA贡献1993条经验 获得超5个赞

Rob Napier 的回答是正确的。

但是,您可能过于努力地实现非阻塞行为,假设它是一种反模式。

使用 Go,您不必担心阻塞。继续,无罪地阻止。它可以使代码更容易编写,尤其是在处理 i/o 时。

CSP 允许您设计数据驱动的并发程序,这些程序可以很好地扩展(因为不会过多地使用互斥锁)。通过通道进行通信的一小组 goroutine 可以表现得像一个更大系统的组件;这些组件(也通过通道进行通信)可以组合成更大的组件;这种模式以越来越大的比例重复。

传统上,人们从顺序代码开始,然后尝试通过添加 goroutine、通道、互斥体等来添加并发。 作为练习,尝试不同的东西:尝试设计一个最大并发的系统- 尽可能深入使用 goroutine 和通道。您可能对您实现的性能不满意……所以也许可以尝试考虑如何通过组合(而不是划分)块来改进它,减少 goroutine 的总数,从而实现更优化的并发性。



查看完整回答
反对 回复 2021-10-04
?
慕丝7291255

TA贡献1859条经验 获得超6个赞

这正是默认情况下select的用途:


var elm myType

select {

case elm = <-myChannel:

default:

}

return elm

elm如果可以,则进行分配,否则返回零值。有关更广泛的示例,请参阅Effective Go中的“泄漏缓冲区” 。


查看完整回答
反对 回复 2021-10-04
  • 2 回答
  • 0 关注
  • 194 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信