考虑以下 Golang 代码:
package main import "fmt" func printRecover() { r := recover() fmt.Println("Recovered:", r) } func main() { defer printRecover() panic("OMG!") }
这个简单的程序成功地发生恐慌并恢复以下输出:
Recovered: OMG!
但是,修改将 printRecover() 包装在另一个延迟函数中的代码会导致不同的结果:
package main import "fmt" func printRecover() { r := recover() fmt.Println("Recovered:", r) } func main() { defer func() { printRecover() }() panic("OMG!") }
在这种情况下,恐慌不会恢复,导致程序崩溃:
Recovered: <nil> panic: OMG! goroutine 1 [running]: main.main() /tmp/sandbox898315096/main.go:15 +0x60
这种行为的解释在于 golang 中的recover() 工作方式。根据语言规范:
The return value of recover is nil if any of the following conditions holds: - panic's argument was nil; - the goroutine is not panicking; - recover was not called directly by a deferred function.
在第一个示例中,recover() 是由延迟函数直接调用的,因此它成功检索了恐慌参数。然而,在第二个示例中,recover() 不是由延迟函数直接调用,而是由本身被延迟函数调用的函数调用。结果recover()返回nil,恐慌没有恢复。
以上是为什么 `recover()` 在 Go 的嵌套延迟函数中不起作用?的详细内容。更多信息请关注PHP中文网其他相关文章!