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

并行执行Go例程的问题

并行执行Go例程的问题

Go
吃鸡游戏 2021-04-26 13:14:21
在我的代码中,有三个并发例程。我尝试简要概述一下我的代码,Routine 1 {do something*Send int to Routine 2Send int to Routine 3Print SomethingPrint Something*do something}Routine 2 {do something*Send int to Routine 1Send int to Routine 3Print SomethingPrint Something*do something}Routine 3 {do something*Send int to Routine 1Send int to Routine 2Print SomethingPrint Something*do something}main {routine1routine2routine3}我希望在执行两个代码之间的某些操作(两个星号之间的代码)时,控制流一定不能进入其他go例程。例如,当例程1正在执行两颗星之间的事件(发送和打印事件)时,例程2和3必须被阻止(执行流不会从例程1传递到例程2或3)。完成最后一个打印事件后,执行流程可能会传递给例程2或3。有人可以通过指定来帮助我,我该如何实现?是否可以通过WaitGroup来实现上述规范?任何人都可以通过举一个简单的示例向我展示如何使用WaitGroup来实现上述指定示例。谢谢。注:可能这是重复的问题本。我试图通过使用同步锁机构,但是,可能是因为我有一个大的代码,这就是为什么我不能把锁定-开锁正常,这是创造死锁情况(或者可能是我的方法是错误产生)。任何人都可以通过一个简单的程序来帮助我,这样我就可以实现这一目标。我给我的代码一个简单的例子,在这里,其中在这里我要放两个打印和发送事件内互斥(日常1),从而程序2不能中断它。你能帮我怎么可能。给出了一种可能的解决方案, http://play.golang.org/p/-uoQSqBJKS给出了错误。
查看完整描述

2 回答

?
慕仙森

TA贡献1827条经验 获得超7个赞

你为什么要这样做?

死锁问题是,如果您不允许安排其他goroutine,则除非有缓冲,否则您的频道发送将无法进行。Go的频道具有有限的缓冲,因此您在耗尽状态之前就陷入了竞争的局面,然后才被发送出去。您可以引入无限缓冲,也可以将每个发送放入自己的goroutine中,但是又可以归结为:为什么要这样做?您想达到什么目的?

另一件事:如果只希望确保* s之间的三组代码互斥,那么可以使用互斥锁。如果要确保没有代码中断块,无论块在何处被挂起,则可能需要使用runtime.LockOSThread和runtime.UnlockOSThread。这些级别很低,您需要知道自己在做什么,而很少需要它们。希望没有其他goroutine运行,您必须要有runtime.GOMAXPROCS(1),这是当前的默认值。


查看完整回答
反对 回复 2021-05-10
?
慕桂英3389331

TA贡献2036条经验 获得超8个赞

回答您的问题的问题在于,似乎没有人了解您的问题的实质。我看到您反复询问大致相同的内容,尽管尚未取得任何进展。这么说并没有冒犯。这是通过建议以其他人可以理解的方式帮助您解决问题的尝试。作为一个可能的好副作用,某些问题确实可以解决,同时可以用一种可以理解的方式向其他人解释。我一个人经历了很多次。

另一个提示可能是显式同步和频道通信的可疑混合。这并不意味着设计必然坏了。它只是在典型/简单的情况下不会发生。再一次,您的问题可能不典型/不平凡。

也许有可能仅使用渠道来重新设计您的问题。实际上,我相信可以在仅使用通道的情况下对涉及显式同步(在Go中)的每个问题进行编码。也就是说,确实可以很容易地通过显式同步编写一些问题。同样,信道通信虽然便宜,却不如大多数同步原语便宜。但这可以在以后的代码运行时得到解决。如果有人说出“ pattern”说出了sync.Mutex将会出现在代码中,那么应该可以切换到它,并且当代码已经可以工作时更容易做到这一点,并希望在进行调整的同时进行测试以观察您的步骤。

尝试像独立代理一样思考您的goroutine,这些代理可以:

  • 独家拥有从通道接收的数据。语言不会强制执行此操作,您必须部署自己的学科。

  • 不要再触摸他们已发送到频道的数据。它遵循第一条规则,但足够重要,必须明确。

  • 通过数据类型与其他代理(goroutine)进行交互,这些数据类型封装了工作流/计算的整个单元。例如,这消除了您之前在“单元”完成之前获得正确数量的通道消息的工作。

  • 对于它们使用的每个通道,必须绝对清楚是否必须取消缓冲该通道,必须为固定数量的项目缓冲该通道或该通道可能未绑定。

  • 如果代理需要自己的信息来完成自己的任务,则不必考虑(了解)其他代理正在做什么,这是更广阔的前景的一部分。

即使使用很少的经验法则,也有望产生出更易于推理且通常不需要任何其他同步的代码。(我现在有意忽略关键任务应用程序的性能问题。)


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

添加回答

举报

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