menu arrow_back 湛蓝安全空间 |狂野湛蓝,暴躁每天 chevron_right All_wiki chevron_right the-way-to-go_ZH_CN chevron_right eBook chevron_right 14.6.md
  • home 首页
  • brightness_4 暗黑模式
  • cloud
    xLIYhHS7e34ez7Ma
    cloud
    湛蓝安全
    code
    Github
    14.6.md
    1.43 KB / 2024-07-16 23:14:29
        # 14.6 协程和恢复 (recover)
    
    一个用到 `recover()` 的程序(参见[第 13.3 节](13.3.md)停掉了服务器内部一个失败的协程而不影响其他协程的工作。
    
    ```go
    func server(workChan <-chan *Work) {
        for work := range workChan {
            go safelyDo(work)   // start the goroutine for that work
        }
    }
    
    func safelyDo(work *Work) {
        defer func() {
            if err := recover(); err != nil {
                log.Printf("Work failed with %s in %v", err, work)
            }
        }()
        do(work)
    }
    ```
    
    上边的代码,如果 `do(work)` 发生 `panic()`,错误会被记录且协程会退出并释放,而其他协程不受影响。
    
    因为 `recover()` 总是返回 `nil`,除非直接在 `defer` 修饰的函数中调用,`defer` 修饰的代码可以调用那些自身可以使用 `panic()` 和 `recover()` 避免失败的库例程(库函数)。举例,`safelyDo()` 中 `defer` 修饰的函数可能在调用 `recover()` 之前就调用了一个 `logging()` 函数,panicking 状态不会影响 `logging()` 代码的运行。因为加入了恢复模式,函数 `do()`(以及它调用的任何东西)可以通过调用 `panic()` 来摆脱不好的情况。但是恢复是在 panicking 的协程内部的:不能被另外一个协程恢复。
    
    
    ## 链接
    
    - [目录](directory.md)
    - 上一节:[通道,超时和计时器](14.5.md)
    - 下一节:[对比新旧模型:任务和工作](14.7.md)
    
    
    links
    file_download