zoukankan      html  css  js  c++  java
  • golang如何使用channel控制goroutine退出

    最经典的处理方式:

    在启动goroutine的时候,传递一个额外的chan型参数,用来接收退出信号,代码如下

    func worker(name string, stopchan chan struct{}) {
        for {
            select {
            case <-stopchan:
                fmt.Println("receive a stop signal, ", name)
                return
            default:
                fmt.Println("I am worker ", name)
                time.Sleep(1 * time.Second)
            }
        }
    
    }

    在main函数中应该如何发送stop信号呢?

    func main() {
        stopCh := make(chan struct{})
        go worker("a", stopCh)
    
        time.Sleep(1 * time.Second)
        stopCh <- struct{}{}
        time.Sleep(3 * time.Second)
    }

    输出:

    I am worker  a
    I am worker  a
    receive a stop signal,  a
    
    Process finished with exit code 0

    ok,从输出可以看出name为a的这个woker在收到信号之后退出了,过了2s后主函数退出

    当我们又2个goroutine的时候情况如何呢?

    func main() {
        stopCh := make(chan struct{})
        go worker("a", stopCh)
        go worker("b", stopCh)
    
        time.Sleep(1 * time.Second)
        stopCh <- struct{}{}
        time.Sleep(3 * time.Second)
    }

    输出:

    I am worker  a
    I am worker  b
    I am worker  b
    I am worker  a
    receive a stop signal,  a
    I am worker  b
    I am worker  b
    I am worker  b

    也就是说a退出了,b没有退出,因为stopCh <- struct{}{}只发送一个信号,被a接收了,b不受影响

    如果想让2个goroutine同时退出,需要这样写:

    close(stopCh)

    再看下输出:

    I am worker  a
    I am worker  b
    I am worker  a
    receive a stop signal,  b
    receive a stop signal,  a
    
    Process finished with exit code 0

    已经全部退出了

    
    
  • 相关阅读:
    最短路径之spfa
    最短路径之Bellman-Ford——解决负权边
    最短路径之Floyd-Warshall算法
    图上最短路径问题
    它们其实都是图(二分图)
    记忆化结果再利用 进一步探讨递推关系
    leetcode 376. 摆动序列 java
    leetcode 368. 最大整除子集 java
    leetcode 96. 不同的二叉搜索树 java
    leetcode 454. 四数相加 II java
  • 原文地址:https://www.cnblogs.com/ksir16/p/8865002.html
Copyright © 2011-2022 走看看