Go 的 Map、Struct、Interface 與 Error 處理
Go 特色
- 執行效能很好
- 每個變數型態在編譯時期就完全決定(statically typed)
- 自動 compile 成為 native 程式碼
- Interfaces
- Functions 可以回傳多重的值
- 內建 concurrency 機制:Goroutines and Channels
Map
宣告 Map
var m map[string]int
Map 的型態是一種 reference ,所以上面範例中 m 的值是 nil
,若嘗試寫入空的 map 會造成 runtime panic。
建立 Map
m = make(map[string]int)
或下面這種方式亦可:
m = map[string]int{}
操作 Map
將 Key uid
對應的值設定成為 5:
m["uid"] = 5
將 uid
的值取出並指定給新的變數 i:
i := m["uid"]
注意當傳入 Key 的值不存在時,預設回傳值是 0:
j := m["notexist"]
// j == 0
取出 Key 的值(下面例子是 i)時順便確認該 Key 是否已經存在,若 Key 存在於 map 當中 ok 的值是 true,反之則為 false:
i, ok := m["uid"]
查看 Map 裡面 items 的數量:
n := len(m)
將 uid
對應的 item 從 map 裡面移除:
delete(m, "uid")
Structs
Go 裡面沒有 Classes,只有 Structs,但 Structs 可以有 functions
宣告 Struct:
type User struct {
Name string // name of the user
Value int // user's value
}
操作 Struct:
var u = User{"Alice", 5}
var u = User{Name: "Alice", Value: 5} // 透過指定 Key 的值來建立一個 struct
var u = []User{{"Alice", 5},{"Bob", 1}} // 初始出一個 structs 的陣列
u.Value = 100
為 Struct 加上 methods:
func (u User) getValue() int {
return u.Value
}
注意上面的方法每次 method 被呼叫的時候,struct 都會被整份複製一次,因此若要透過 method 改變 struct 的值必須使用下面的方法:
func (u *User) add(n int) {
u.Value += n
}
Pointers
p := User{"Alice", 5} // p 是個 User
q := &p // q 是指到 User 的 Pointer
Interface
宣告 Interface:
type Greeting interface {
Hello() string
}
不需要在 type 中宣告 implement 某個 interface,假如 interface 中的 functions 都有被對應到,自動滿足成為該 interface 的一員:
type Foo struct {}
func (foo Foo) Hello() string {
return "Hello!"
}
Errors
GoLang 沒有 exception handling,function 多一個型態為 Error 的回傳值就可以在執行時檢查是否有錯誤:
func getValue() (int, error) {
}
func main() {
result, error := getValue()
if (error != nil) {
// 處理遇到的錯誤
} else {
// 沒有錯誤
}
}
而 Error 是一個內建的 interface:
type error interface {
Error() string
}
操作 Error
var err error = errors.New("A new error")
fmt.Println(err.Error()) // A new error
或透過 Errorf 處理錯誤訊息:
err = fmt.Errorf("%s", "test error for fmt.Errorf")
fmt.Println(err.Error())
定義客製化型態的 Error:
type CustomError struct {
Path string
Err error
}
func (c *CustomError) Error() string {
return e.Path + ": " + e.Err.Error()
}
相關參考
Go lang cheat sheet: https://github.com/a8m/go-lang-cheat-sheet