Table of contents
Bài này ghi lại những thứ tôi hiểu về hàm init trong Go.
Khi tạo ứng dụng với ngôn ngữ Go, bạn cần khởi tạo biến cùng giá trị của chúng. Một trong những cách để làm điều này là khởi tạo chúng ở đầu hàm main()
hoặc khởi tạo chúng như biến global. Hàm init()
cho phép bạn chạy code trước hàm main()
và sau khi biến global được khởi tạo.
Concepts
Hàm init()
sẽ được gọi trước hàm main()
theo thứ tự như hình dưới.
Requirements
Để chạy được phần code demo, bạn cần cài Go và nodemon. Bạn có thể chọn bất kỳ editor nào. Tôi dùng Visual Studio Code.
Demo
- Hàm
init()
chỉ chạy một lần. - Hàm
init()
sẽ chạy sau khi biến global của package được khởi tạo và trước hàmmain()
.
package main
import (
"fmt"
)
func main() {
fmt.Println("run main")
}
func init() {
fmt.Println("init package main")
fmt.Println("x =", x)
}
var x int = 1 // biến global
nodemon --exec go run main.go --signal SIGTERM
init package main
x = 1
run main
- Hàm
init()
bên trong package sẽ chạy khi import package bất kể bạn có sử dụng package này hay không.
package main
import (
"fmt"
_ "learn/internal/collections"
)
func main() {
fmt.Println("run main")
}
package collections
import "fmt"
func init() {
fmt.Println("init package collections")
}
func main() {
fmt.Println("run main in collections")
}
init package collections
run main
- Nếu có nhiều hàm
init()
trong một file thì thứ tự chạyinit()
sẽ từ trên xuống dưới.
package main
import (
"fmt"
)
func init() {
fmt.Println("run init 1")
}
func init() {
fmt.Println("run init 2")
}
func main() {
fmt.Println("run main")
}
run init 1
run init 2
run main
- Nếu có nhiều hàm
init()
giữa các file trong một package, thứ tự chạy theo tên file tăng dần theo bảng chữ cái tiếng anh.
package main
import (
"fmt"
_ "learn/pkg/collections"
_ "learn/pkg/rabbits"
)
func init() {
fmt.Println("init package main")
}
func main() {
fmt.Println("run main")
}
package collections
import "fmt"
func init() {
fmt.Println("init package collections")
}
package rabbits
import "fmt"
func init() {
fmt.Println("init package rabbits")
}
init package collections
init package rabbits
init package main
Nhược điểm
Sau đây là một vài nhược điểm của việc dùng hàm init()
:
- Làm chậm thời gian khởi động của ứng dụng.
- Hàm
init()
sẽ được gọi ngay khi bạn import package bất kể có cần hay không. - Nếu hàm
init()
sửa giá trị của biến global, nó sẽ không được gọi khi chạy test.