【问题标题】:Select statement channel example选择语句通道示例
【发布时间】:2018-10-06 22:42:51
【问题描述】:

我是 golang 的新手,并尝试了解 select 语句是如何工作的 https://www.tutorialspoint.com/go/go_select_statement.htm

package main

import "fmt"

func main() {
   var c1, c2, c3 chan int
   var i1, i2 int
   select {
      case i1 = <-c1:
         fmt.Printf("received ", i1, " from c1\n")
      case c2 <- i2:
         fmt.Printf("sent ", i2, " to c2\n")
      case i3, ok := (<-c3):  // same as: i3, ok := <-c3
         if ok {
            fmt.Printf("received ", i3, " from c3\n")
         } else {
            fmt.Printf("c3 is closed\n")
         }
      default:
         fmt.Printf("no communication\n")
   }    
}   

此时没有关于频道的解释。现在我不知道如何触发另一个输出为“无通信”。

谁能给我一个例子吗?

【问题讨论】:

  • 参加围棋之旅。这可能会以更易于理解的顺序来解释。

标签: select go concurrency channel


【解决方案1】:

select 语句选择一个case,其通信操作不会阻塞。如果有多个案例的通讯。 op不会阻塞,随机选择一个。

由于在示例中所有通信操作都会阻塞,并且由于提供了 default,因此将执行该操作。

要“触发”另一个案例,您必须确保其通讯。 op 不会阻塞。在示例中,没有人从案例中使用的任何通道发送或接收任何内容。地狱,他们甚至没有初始化。并且从nil 通道发送和接收都将永远阻塞(有关详细信息,请参阅How does a non initialized channel behave?)。所以你应该这样做:初始化一个通道并从它发送/接收,你想要触发的那个。例如:

c1 = make(chan int, 1)
c1 <- 1

这个 sn-p 使用缓冲区 1 初始化 c1 通道,并在其上发送一个值。所以在这之后的select语句中,通信操作i1 = &lt;-c1不会阻塞,所以会选择这个,输出是:

received  1  from c1

Go Playground 上试试。 (注意:我将所有Printf() 调用更改为Println()。)

请注意,在其他 goroutine 上,在通道上发送/接收可能同时发生。为简单起见,我选择了缓冲通道和相同的 goroutine,这样即使在 Go Playground 上,它的行为也符合您的预期。

更多频道信息:What are golang channels used for?

【讨论】:

  • 谢谢,这正是我想要的。
猜你喜欢
  • 2017-12-29
  • 1970-01-01
  • 2012-11-10
  • 2013-11-20
  • 1970-01-01
  • 2023-04-11
  • 2021-10-09
  • 2020-07-30
  • 2020-12-13
相关资源
最近更新 更多