zoukankan      html  css  js  c++  java
  • golang channel几点总结

    golang提倡使用通讯来共享数据,而不是通过共享数据来通讯。channel就是golang这种方式的体现。

    Channel

    在golang中有两种channel:带缓存的和不带缓存。

    • 带缓存的channel,也就是可以异步收发的。
    • 不带缓存的channel,也就是同步收发的。

    发送:

    • 向 nil channel 发送数据,阻塞。
    • 向 closed channel 发送数据,出错。
    • 同步发送: 如有接收者,交换数据。否则排队、阻塞。
    • 异步发送: 如有空槽,拷⻉贝数据到缓冲区。否则排队、阻塞。

    接收:

    • 从 nil channel 接收数据,阻塞。
    • 从 closed channel 接收数据,返回已有数据或零值。
    • 同步接收: 如有发送者,交换数据。否则排队、阻塞。
    • 异步接收: 如有缓冲项,拷⻉贝数据。否则排队、阻塞。

    底层实现

    使用channel时,多个goroutine并发发送和接收,却无需加锁,为什么呢?

    其实,是由底channel层实现做支撑的。

    channel的具体定义参见/usr/local/go/src/runtime/chan.go

    type hchan struct {
            qcount   uint           // total data in the queue
            dataqsiz uint           // size of the circular queue
            buf      unsafe.Pointer // points to an array of dataqsiz elements
            elemsize uint16
            closed   uint32
            elemtype *_type // element type
            sendx    uint   // send index
            recvx    uint   // receive index
            recvq    waitq  // list of recv waiters
            sendq    waitq  // list of send waiters
    
            // lock protects all fields in hchan, as well as several
            // fields in sudogs blocked on this channel.
            //
            // Do not change another G's status while holding this lock
            // (in particular, do not ready a G), as this can deadlock
            // with stack shrinking.
            lock mutex
    }
    

    可以看到,有lock字段,在使用channel进行发送和接收的时候,会进行加锁保护。

    参考

    雨痕《Go学习笔记 第四版》

  • 相关阅读:
    ES6 数组下
    ES6 ---数组(上部分)
    ES6---函数
    ES6---字符串
    自适应网页设计(Responsive Web Design)
    HTML Meta中添加X-UA-Compatible和IE=Edge,chrome=1有什么作用?
    mysql潜在的危险kill
    shell脚本加密
    Linux安全知识总结
    nginx 解决400 bad request 的方法(转载)
  • 原文地址:https://www.cnblogs.com/lanyangsh/p/9970602.html
Copyright © 2011-2022 走看看