Golang學(xué)習(xí)筆記之延遲函數(shù)(defer)的使用小結(jié)
golang的defer優(yōu)雅又簡潔, 是golang的亮點之一。defer在聲明時不會立即執(zhí)行,而是在函數(shù)return后,再按照先進后出的原則依次執(zhí)行每個defer,一般用于釋放資源、清理數(shù)據(jù)、記錄日志、異常處理等。
關(guān)鍵字defer于注冊延遲調(diào)用。這些調(diào)用直到 ret 前才被執(zhí)行,通常用于釋放資源或錯誤處理。
一、當(dāng)defer被聲明時,其參數(shù)就會被實時解析
func a() {
i := 0
defer fmt.Println(i) //輸出0,因為i此時就是0
i++
defer fmt.Println(i) //輸出1,因為i此時就是1
return
}
二、當(dāng)一個函數(shù)內(nèi)多次調(diào)用 defer 時,Go 會把 defer 調(diào)用放入到一個棧中,隨后按照先進后出的順序執(zhí)行。
func main() {
defer fmt.Println("1")
defer fmt.Println("2")
defer fmt.Println("3")
defer fmt.Println("4")
}
輸出順序為4321
使用defer逆序輸出字符串
name := "Naveen你好"
fmt.Printf("%s\n", string(name))
fmt.Printf("逆序:")
defer fmt.Printf("\n")
for _, v := range []rune(name) {
defer fmt.Printf("%c", v)
}
輸出:
Naveen你好
逆序:好你neevaN
三、defer 的實際應(yīng)用
func (r rect) area(wg *sync.WaitGroup) {
if r.length < 0 {
fmt.Printf("rect %v's length should be greater than zero\n", r)
wg.Done()
return
}
if r.width < 0 {
fmt.Printf("rect %v's width should be greater than zero\n", r)
wg.Done()
return
}
area := r.length * r.width
fmt.Printf("rect %v's area %d\n", r, area)
wg.Done()
}
我們會發(fā)現(xiàn)上面wg.Done()被調(diào)用多次我們可以使用defer來優(yōu)化代碼
func (r rect) area(wg *sync.WaitGroup) {
defer wg.Done()
if r.length < 0 {
fmt.Printf("rect %v's length should be greater than zero\n", r)
return
}
if r.width < 0 {
fmt.Printf("rect %v's width should be greater than zero\n", r)
return
}
area := r.length * r.width
fmt.Printf("rect %v's area %d\n", r, area)
}
使用defer延時調(diào)用,會在程序結(jié)束之前調(diào)用
下面舉個例子:
package main
import "fmt"
func deferTest(number int) int {
defer func() {
number++
fmt.Println("three:", number)
}()
defer func() {
number++
fmt.Println("two:", number)
}()
defer func() {
number++
fmt.Println("one:", number)
}()
return number
}
func main() {
fmt.Println("函數(shù)返回值:", deferTest(0))
}
上面的代碼打印的結(jié)果是:
one: 1
two: 2
three: 3
函數(shù)返回值: 0
PS:defer 有一個重要的特性,即便函數(shù)拋出了異常,defer也會被執(zhí)行的。這樣就不會因為程序出現(xiàn)了錯誤,導(dǎo)致資源不會被釋放了。
以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
聊聊go xorm生成mysql的結(jié)構(gòu)體問題
這篇文章主要介紹了go xorm生成mysql的結(jié)構(gòu)體問題,本文給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友參考下吧2022-03-03
go語言實現(xiàn)http服務(wù)端與客戶端的例子
今天小編就為大家分享一篇go語言實現(xiàn)http服務(wù)端與客戶端的例子,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧2019-08-08

