「賴其前世。defer營護。今為LIFO。錯誤處理。」
在過去、今生曾經延遲過的程式,這個程式後進先出,可能在資源管理,或是在執行錯誤處理。
Functions
是一種用於執行特定任務或操作的程式碼塊,它可以接受 零個
或 多個
輸入參數,並且可以返回一個或多個值。
定義函數使用 func
關鍵字,後面跟著 函數名稱
、參數列表
和返回值的類型
。函數可以有零個或多個參數,也可以有零個或多個返回值。
func 函數名稱(參數列表) 返回值類型 {
// 函數內容
}
要呼叫函數,只需使用函數名稱,並將必要的參數傳遞給它。如果函數有返回值,則可以將其存儲在變數中。
result := 函數名稱(參數值)
package main
import "fmt"
// 定義一個函數,計算兩個整數的總和
func 加法(x, y int) int {
return x + y
}
func main() {
// 呼叫加法函數並將結果存儲在變數中
結果 := 加法(5, 3)
// 輸出結果
fmt.Println("5 + 3 =", 結果)
}
5 + 3 = 8
可以在函數的返回值部分指定 多個返回值
,用 逗號
分隔。函數可以返回 不同類型
的 多個值
。
func 函數名稱(參數列表) (返回值1類型, 返回值2類型, ...) {
// 函數內容
return 返回值1, 返回值2, ...
}
舉例:
package main
import "fmt"
// 定義一個函數,返回兩個整數的和與積
func 加和積(x, y int) (int, int) {
和 := x + y
積 := x * y
return 和, 積
}
func main() {
// 呼叫加和積函數
總和, 乘積 := 加和積(5, 3)
// 輸出結果
fmt.Printf("總和:%d,乘積:%d\n", 總和, 乘積)
}
可以使用 Named Result Parameters
來為函數的返回值 指定名稱
。這種技巧可以在函數內更容易使用和操作返回值。
當定義一個函數時,可以在函數簽名中指定返回值的名稱。而無需使用 return 。
func 函數名稱(參數列表) (返回值名稱1 返回值類型1, 返回值名稱2 返回值類型2, ...) {
// 函數內容
// 直接使用返回值名稱來賦值
返回值名稱1 = 值1
返回值名稱2 = 值2
}
當呼叫一個返回命名返回值參數的函數時,可以直接使用這些名稱來訪問返回的值,而無需使用變數接收。
結果1, 結果2 := 函數名稱(參數值)
舉例:
package main
import "fmt"
// 定義一個函數,計算兩個整數的和與積,並使用命名返回值參數
func 加和積(x, y int) (和 int, 積 int) {
和 = x + y
積 = x * y
return // 無需使用 return 關鍵字,因為已經命名了返回值參數
}
func main() {
// 呼叫加和積函數
總和, 乘積 := 加和積(5, 3)
// 直接使用命名返回值參數的名稱
fmt.Printf("總和:%d,乘積:%d\n", 總和, 乘積)
}
總和:8,乘積:15
defer 是一個用於 延遲執行
某個函數宣告。通常用於確保某些程式碼在目前函數執行完畢之前或在目前函數返回之前執行,無論是正常執行還是發生異常。 defer
的主要用途是在 資源管理
像是文件關閉、資料庫連接關閉等和清理工作上。
當包含 defer 的函數執行到結束時,被延遲的函數會按照先進後出(LIFO)的順序執行,也就是說最後一個 defer 的函數最先執行。
package main
import "fmt"
func main() {
// 延遲執行函數 foo,它會在 main 函數執行完畢之前執行
defer foo()
fmt.Println("在 defer 前面")
// 這裡觸發一個異常
panic("發生異常")
// 這個程式不會執行,因為上面觸發了異常
fmt.Println("在 defer 後面")
}
func foo() {
fmt.Println("foo 函數被呼叫")
}
在 defer 前面
foo 函數被呼叫
panic: 發生異常
goroutine 1 [running]:
main.main()
/Users/yzj90596/Desktop/readme/main.go:13 +0x8b
exit status 2
不是不報,時候未到,時候是誰決定的? 不知道
因果defer何曾饒過誰!
但 defer
會 延遲執行
、 LIFO
、資源管理
還有 錯誤處理
。