type assertion(中文名叫:型別斷言),通過它可以做到以下幾件事情
檢查i
是否為 nil
檢查i
儲存的值是否為某個型別
具體的使用方式有兩種:
第一種:
t := i.(t)
這個表示式可以斷言乙個介面物件(i)裡不是 nil,並且介面物件(i)儲存的值的型別是 t,如果斷言成功,就會返回值給 t,如果斷言失敗,就會觸發 panic。
來寫段**試驗一下
package main
import "fmt"
func main() = 10
t1 := i.(int)
fmt.println(t1)
fmt.println("*****分隔線*****")
t2 := i.(string)
fmt.println(t2)
}
執行後輸出如下,可以發現在執行第二次斷言的時候失敗了,並且觸發了 panic
10
*****分隔線*****
panic: inte***ce conversion: inte***ce {} is int, not string
goroutine 1 [running]:
main.main()
e:/goplayer/src/main.go:12 +0x10e
exit status 2
如果要斷言的介面值是 nil,那我們來看看也是不是也如預期一樣會觸發panic
package main
func main() // nil
var _ = i.(inte***ce{})
}
輸出如下,確實是會 觸發 panic
panic: inte***ce conversion: inte***ce is nil, not inte***ce {}
goroutine 1 [running]:
main.main()
e:/goplayer/src/main.go:5 +0x34
exit status 2
第二種
t, ok:= i.(t)
和上面一樣,這個表示式也是可以斷言乙個介面物件(i)裡不是 nil,並且介面物件(i)儲存的值的型別是 t,如果斷言成功,就會返回其型別給 t,並且此時 ok 的值 為 true,表示斷言成功。
如果介面值的型別,並不是我們所斷言的 t,就會斷言失敗,但和第一種表示式不同的事,這個不會觸發 panic,而是將 ok 的值設為 false ,表示斷言失敗,此時t 為 t 的零值。
稍微修改下上面的例子,如下
package main
import "fmt"
func main() = 10
t1, ok := i.(int)
fmt.printf("%d-%t\n", t1, ok)
fmt.println("*****分隔線1*****")
t2, ok := i.(string)
fmt.printf("%s-%t\n", t2, ok)
fmt.println("*****分隔線2*****")
var k inte***ce{} // nil
t3, ok := k.(inte***ce{})
fmt.println(t3, "-", ok)
fmt.println("*****分隔線3*****")
k = 10
t4, ok := k.(inte***ce{})
fmt.printf("%d-%t\n", t4, ok)
t5, ok := k.(int)
fmt.printf("%d-%t\n", t5, ok)
}
執行後輸出如下,可以發現在執行第二次斷言的時候,雖然失敗了,但並沒有觸發了 panic。
10-true
*****分隔線1*****
-false
*****分隔線2*****
- false
*****分隔線3*****
10-true
10-true
上面這段輸出,你要注意的是第二個斷言的輸出在-false
之前並不是有沒有輸出任何 t2 的值,而是由於斷言失敗,所以 t2 得到的是 string 的零值也是""
,它是零長度的,所以你看不到其輸出。
如果需要區分多種型別,可以使用 type switch 斷言,這個將會比乙個乙個進行型別斷言更簡單、直接、高效。
package main
import "fmt"
func findtype(i inte***ce{})
}func main() // nil
findtype(k)
findtype(10.23) //float64
}
輸出如下
10 is int
hello is string
is nil
10.23 not type matched
額外說明一下:
01. 開發環境的搭建(goland & vs code)
02. 學習五種變數建立的方法
03. 詳解資料型別:**整形與浮點型**
04. 詳解資料型別:byte、rune與string
05. 詳解資料型別:陣列與切片
06. 詳解資料型別:字典與布林型別
07. 詳解資料型別:指標
08. 物件導向程式設計:結構體與繼承
09. 一篇文章理解 go 裡的函式
10. go語言流程控制:if-else 條件語句
11. go語言流程控制:switch-case 選擇語句
12. go語言流程控制:for 迴圈語句
13. go語言流程控制:goto 無條件跳轉
14. go語言流程控制:defer 延遲呼叫
15. 物件導向程式設計:介面與多型
16. 關鍵字:make 和 new 的區別?
17. 一篇文章理解 go 裡的語句塊與作用域
18. 學習 go 協程:goroutine
19. 學習 go 協程:詳解通道/通道
20. 幾個通道死鎖經典錯誤案例詳解
21. 學習 go 協程:waitgroup
22. 學習 go 協程:互斥鎖和讀寫鎖
23. go 裡的異常處理:panic 和 recover
24. 超詳細解讀 go modules 前世今生及入門使用
25. go 語言中關於包匯入必學的 8 個知識點
26. 如何開源自己寫的模組給別人用?
27. 說說 go 語言中的型別斷言?
28. 這五點帶你理解go語言的select用法
go語言的型別斷言 Type Assertion
x.t 檢查x的動態型別是否是t,其中x必須是介面值。如果t是具體型別 型別斷言檢查x的動態型別是否等於具體型別t。如果檢查成功,型別斷言返回的結果是x的動態值,其型別是t。換句話說,對介面值x斷言其動態型別是具體型別t,若成功則提取出x的具體值。如果檢查失敗則panic。例如 var w io.w...
GO語言中的StructTag型別
structtag是什麼?在go語言裡,structtag是乙個標記字串,此字串可跟隨在struct中欄位定義的後面。structtag就是一系列的 key value 形式的組合,其中key是乙個不可為空的字串,key value組合可以有多個,空格分隔。structtag有什麼用?structt...
C語言中的EOF是什麼?
日期 2011年11月12日 我學習c語言的時候,遇到的乙個問題就是eof。它是end of file的縮寫,表示 文字流 stream 的結尾。這裡的 文字流 可以是檔案 file 也可以是標準輸入 stdin 比如,下面這段 就表示,如果不是檔案結尾,就把檔案的內容複製到螢幕上。int c wh...