Go by Example Series: non-blocking Channels operation

Source: Internet
Author: User
This is a creation in Article, where the information may have evolved or changed.

Note: This series of articles are all from the go by Example series translation, the level of personal translation and understanding is limited, for more precise understanding, please see the original go by example:non-blocking Channel Operations.

In Channels (channel? ) on the basic sends (send) and receives (receive) is blocking mode. Nonetheless, we can use SELECT and a default clause to sends, receives, or even non-blocking multiple choices.

Note: Thanks to the @lidashuang note, the article is not described clearly, modified as follows: Select is blocked by default, but in the select also has the default syntax, which is similar to the Switch,default when the channel is not ready to listen , which is performed by default (select no longer blocks waiting for channel)
At the same time, sometimes there will be goroutine blocking situation, you can use the Select Set timeout to avoid the whole program into blocking state

Code version One

The code is as follows:

package mainimport "fmt"func main() {    messages := make(chan string)    signals := make(chan bool) /**这里是一个非阻塞 receive。如果在 messages 上的值是可用的,那 select 将 <-messages 的值带上,执行 <-messages 下面的println语句。如果不是,它将立即带上 default 的值,执行 default 下面的println语句**/    select {    case msg := <-messages:        fmt.Println("received message", msg)    default:        fmt.Println("no message received")    }/**一个非阻塞 send 的类似工作 **/    msg := "hi"    select {    case messages <- msg:        fmt.Println("sent message", msg)    default:        fmt.Println("no message sent")    }/**我们可以用在 default 之上使用多个 cases 来实现一个非阻塞的多路 select。在这里我们尝试在 messages 和 signals 上实现非阻塞 receives。**/    select {    case msg := <-messages:        fmt.Println("received message", msg)    case sig := <-signals:        fmt.Println("received signal", sig)    default:        fmt.Println("no activity")    }}

The result output of the final program is:

$ go run non-blocking-channel-operations.go no message receivedno message sentno activity

Code version Two

The code is as follows:

package mainimport (    "fmt")func main() {    // messages := make(chan string)    //如果不加缓存的话,就全部会选择defalut    messages := make(chan string, 1) //加了缓存的话,会选择对应的    signals := make(chan bool)    // messages <- "test"    select {    case msg := <-messages:        fmt.Println("received message", msg) //因为messages目前本身还没有值,因此选择default执行    default:        fmt.Println("no message received")    }    // go func() {    msg := "hi world"    // }()    select {    case messages <- msg:        fmt.Println("sent message", msg) //因为channels有缓存,所以这里的msg发送到 channels messages 能处理,不会被阻塞住    default:        fmt.Println("no message sent")    }    select {    case msg := <-messages:        fmt.Println("received message", msg) //因为messages已经有值了,所以会选择这个case执行    case sig := <-signals:        fmt.Println("received signal", sig)    default:        fmt.Println("no activity")    }}

The output results are as follows:

$ go run non-blocking-channel-operations.go no message receivedsent message hi worldreceived message hi world   

Code version Three

The code is as follows:

package mainimport (    "fmt")func main() {    // messages := make(chan string)    //如果不加缓存的话,就全部会选择defalut    messages := make(chan string, 1) //加了缓存的话,会选择对应的    signals := make(chan bool)    messages <- "test"    select {    case msg := <-messages:        fmt.Println("received message", msg) //messages已经有值,因此选择这个case执行    default:        fmt.Println("no message received")    }    // go func() {    msg := "hi world"    // }()    select {    case messages <- msg:        fmt.Println("sent message", msg)    default:        fmt.Println("no message sent")    }    select {    case msg := <-messages:        fmt.Println("received message", msg)    case sig := <-signals:        fmt.Println("received signal", sig)    default:        fmt.Println("no activity")    }}

The result of the code output is as follows:

$ go run non-blocking-channel-operations.go received message testsent message hi worldreceived message hi world

Code version Four

The code is as follows:

package mainimport (    "fmt")func main() {    messages := make(chan string) //如果不加缓存的话,就全部会选择defalut    //messages := make(chan string, 1) //加了缓存的话,会选择对应的    signals := make(chan bool)    messages <- "test" //因为该channels没有缓存,而其又赋值了,会到时死锁。    select {    case msg := <-messages:        fmt.Println("received message", msg)    default:        fmt.Println("no message received")    }    // go func() {    msg := "hi world"    // }()    select {    case messages <- msg:        fmt.Println("sent message", msg)    default:        fmt.Println("no message sent")    }    select {    case msg := <-messages:        fmt.Println("received message", msg)    case sig := <-signals:        fmt.Println("received signal", sig)    default:        fmt.Println("no activity")    }}

The result of the code output is:

fatal error: all goroutines are asleep - deadlock!

Runtime Goroutine

There are several functions in the runtime package that deal with Goroutine

    1. Goexit-Exits the currently executing goroutine, but the defer function also continues to invoke
    2. Gosched-yields the execution permission of the current goroutine, the scheduler schedules other waiting tasks to run, and resumes execution from that location the next time
    3. NUMCPU-Returns the number of CPU cores
    4. Numgoroutine-Returns the total number of tasks being executed and queued
    5. Gomaxprocs-Used to set the number of CPU cores that can be run
Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.