golang学习笔记—— defer、panic 和 recover 处理错误

本文详细介绍了Go语言中的defer、panic和recover函数,它们在异常处理中的角色,包括如何使用defer推迟函数执行、panic终止程序并记录堆栈信息、以及recover用于捕获和处理panic。还探讨了如何在实际编程中正确运用这些机制以实现类似try-catch的错误处理方式。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

defer、panic 和 recover函数

defer 函数

在 Go 中,defer 语句会推迟函数(包括任何参数)的运行,直到包含 defer 语句的函数完成。 通常情况下,当你想要避免忘记任务(例如关闭文件或运行清理进程)时,可以推迟某个函数的运行。

可以根据需要推迟任意多个函数。 defer 语句按逆序运行,先运行最后一个,最后运行第一个。

panic 函数

运行时错误会使 Go 程序崩溃,例如尝试通过使用超出范围的索引或取消引用 nil 指针来访问数组。 你也可以强制程序崩溃。

内置 panic() 函数可以停止 Go 程序中的正常控制流。 当你使用 panic 调用时,任何延迟的函数调用都将正常运行。 进程会在堆栈中继续,直到所有函数都返回。 然后,程序会崩溃并记录日志消息。 此消息包含错误信息和堆栈跟踪,有助于诊断问题的根本原因。

调用 panic() 函数时,可以添加任何值作为参数。 通常,你会发送一条错误消息,说明为什么会进入紧急状态。

recover 函数

有时,你可能想要避免程序崩溃,改为在内部报告错误。 或者,你可能想要先清理混乱情况,然后再让程序崩溃。 例如,你可能想要关闭与某个资源的连接,以免出现更多问题。

Go 提供内置 recover() 函数,让你可以在程序崩溃之后重新获得控制权。 你只会在你同时调用 defer 的函数中调用 recover。 如果调用 recover() 函数,则在正常运行的情况下,它会返回 nil,没有任何其他作用。

异常处理

Golang 没有结构化异常,使用 panic 抛出错误,recover 捕获错误。

异常的使用场景简单描述:Go中可以抛出一个panic的异常,然后在defer中通过recover捕获这个异常,然后正常处理。

panic:

1、内置函数
2、假如函数F中书写了panic语句,会终止其后要执行的代码,在panic所在函数F内如果存在要执行的defer函数列表,按照defer的逆序执行
3、返回函数F的调用者G,在G中,调用函数F语句之后的代码不会执行,假如函数G中存在要执行的defer函数列表,按照defer的逆序执行
4、直到goroutine整个退出,并报告错误

recover:

1、内置函数
2、用来控制一个goroutine的panicking行为,捕获panic,从而影响应用的行为
3、一般的调用建议
    a). 在defer函数中,通过recever来终止一个goroutine的panicking过程,从而恢复正常代码的执行
    b). 可以获取通过panic传递的error

注意:

  • 1.利用recover处理panic指令,defer 必须放在 panic 之前定义,另外 recover 只有在 defer 调用的函数中才有效。否则当panic时,recover无法捕获到panic,无法防止panic扩散。
  • 2.recover 处理异常后,逻辑并不会恢复到 panic 那个点去,函数跑到 defer 之后的那个点。
  • 3.多个 defer 会形成 defer 栈,后定义的 defer 语句会被最先调用。
package main

func main() {
   
    test()
}

func test() {
   
    defer func() {
   
        if err := recover(); err != nil {
   
            println(err.(string)) // 将 interface{} 转型为具体类型。
        }
    }()

    panic("panic error!")
}  

输出结果:

panic error!

由于 panic、recover 参数类型为 interface{},因此可抛出任何类型对象。

    func panic(v interface{})
    func recover() interface{}

向已关闭的通道发送数据会引发panic

package main

import (
    "fmt"
)

func main() {
   
    defer func(
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值