网站首页 > 博客文章 正文
在 Go 语言中,defer 是一个非常强大的关键字,用于延迟执行函数或方法调用。defer 通常用于资源释放、错误处理、日志记录等场景,以确保某些操作在函数返回前被执行。以下是 defer 的使用教程:
一、defer的基本用法
defer 的语法非常简单,只需在函数调用前加上 defer 关键字即可。被 defer 的语句会在 函数返回前 执行,即使函数中途发生错误或提前返回。
示例 1:基本用法
package main
import "fmt"
func main() {
defer fmt.Println("World") // 这行会在 main 函数返回前执行
fmt.Println("Hello")
}
输出:
Hello
World
二、defer的执行顺序
如果有多个 defer 语句,它们会以 后进先出(LIFO) 的顺序执行,即最后一个 defer 最先执行。
示例 2:多个defer
package main
import "fmt"
func main() {
defer fmt.Println("First")
defer fmt.Println("Second")
defer fmt.Println("Third")
}
输出:
Third
Second
First
三、defer的常见用途
1. 资源释放
defer 通常用于确保资源(如文件、数据库连接、锁等)在函数退出时被正确释放。
示例 3:文件操作
package main
import (
"fmt"
"os"
)
func main() {
file, err := os.Open("example.txt")
if err != nil {
fmt.Println("Error:", err)
return
}
defer file.Close() // 确保文件关闭
// 文件操作
// ...
}
2. 错误处理
defer 可以用于在函数返回前执行一些错误处理操作。
示例 4:错误处理
package main
import "fmt"
func divide(a, b int) (result int, err error) {
defer func() {
if r := recover(); r != nil { // 捕获 panic
err = fmt.Errorf("runtime panic: %v", r)
}
}()
if b == 0 {
panic("division by zero") // 触发 panic
}
return a / b, nil
}
func main() {
result, err := divide(10, 0)
if err != nil {
fmt.Println("Error:", err)
return
}
fmt.Println("Result:", result)
}
输出:
Error: runtime panic: division by zero
3. 日志记录
defer 可以用于在函数退出时记录日志。
示例 5:日志记录
package main
import "fmt"
func main() {
defer fmt.Println("Function main completed") // 记录函数完成
fmt.Println("Function main started")
}
输出:
Function main started
Function main completed
四、defer的注意事项
1.defer的参数是立即求值的
defer 语句中的函数参数会在 defer 语句执行时立即求值,而不是在函数返回时。
示例 6:参数求值
package main
import "fmt"
func main() {
i := 0
defer fmt.Println("Deferred:", i) // 参数 i 立即求值
i++
fmt.Println("Current:", i)
}
输出:
Current: 1
Deferred: 0
2.defer与返回值
如果函数有返回值,defer 可以修改返回值。
示例 7:修改返回值
package main
import "fmt"
func main() {
fmt.Println("Result:", test())
}
func test() (result int) {
defer func() {
result = 100 // 修改返回值
}()
return 10
}
输出:
Result: 100
3.defer的性能开销
defer 的使用会引入一定的性能开销,因为它需要在函数返回前执行额外的操作。在性能敏感的场景中,应谨慎使用。
五、总结
defer 是 Go 语言中非常有用的特性,能够简化资源管理和错误处理。通过合理使用 defer,可以提高代码的可读性和健壮性。主要用途包括:
- 资源释放(如文件关闭、解锁等)。
- 错误处理和恢复(如捕获 panic)。
- 日志记录(如记录函数执行时间)。
掌握 defer 的使用技巧,能够让你的 Go 代码更加优雅和高效。
猜你喜欢
- 2025-03-17 golang使用logrus生成日志(golang gc日志)
- 2025-03-17 在Golang中使用日志模块(golang 日志处理)
- 2025-03-17 golang性能优化实践(golang 性能优化)
- 2025-03-17 Golang的日志库(go日志框架)
- 2025-03-17 超干货:Golang 简洁架构实战(golang技巧)
- 2025-03-17 Golang 如何实现定时任务(golang定时任务调度)
- 2025-03-17 每日一库之 logrus 日志使用教程(log日志怎么打开)
- 2025-03-17 Golang:将日志以Json格式输出到Kafka
- 2025-03-17 运维大神如何使用 Golang 日志监控应用程序
你 发表评论:
欢迎- 374℃手把手教程「JavaWeb」优雅的SpringMvc+Mybatis整合之路
- 369℃用AI Agent治理微服务的复杂性问题|QCon
- 360℃初次使用IntelliJ IDEA新建Maven项目
- 353℃Maven技术方案最全手册(mavena)
- 351℃安利Touch Bar 专属应用,让闲置的Touch Bar活跃起来!
- 349℃InfoQ 2024 年趋势报告:架构篇(infoq+2024+年趋势报告:架构篇分析)
- 348℃IntelliJ IDEA 2018版本和2022版本创建 Maven 项目对比
- 344℃从头搭建 IntelliJ IDEA 环境(intellij idea建包)
- 最近发表
- 标签列表
-
- powershellfor (55)
- messagesource (56)
- aspose.pdf破解版 (56)
- promise.race (63)
- 2019cad序列号和密钥激活码 (62)
- window.performance (66)
- qt删除文件夹 (72)
- mysqlcaching_sha2_password (64)
- ubuntu升级gcc (58)
- nacos启动失败 (64)
- ssh-add (70)
- jwt漏洞 (58)
- macos14下载 (58)
- yarnnode (62)
- abstractqueuedsynchronizer (64)
- source~/.bashrc没有那个文件或目录 (65)
- springboot整合activiti工作流 (70)
- jmeter插件下载 (61)
- 抓包分析 (60)
- idea创建mavenweb项目 (65)
- vue回到顶部 (57)
- qcombobox样式表 (68)
- vue数组concat (56)
- tomcatundertow (58)
- pastemac (61)
本文暂时没有评论,来添加一个吧(●'◡'●)