在 Go 语言中,. (T) 是类型断言(Type Assertion)的语法,用于检查接口值的动态类型是否为指定类型 T,或判断接口值是否实现了指定接口类型 T。
一、语法形式
类型断言有两种常用形式:
- 基础形式(仅判断类型,不处理错误):
value.(T)
value必须是一个接口类型的变量(不能是具体类型变量)。T可以是具体类型(如int、string)或接口类型。
如果断言成功,返回 value 动态值的 具体类型值;如果失败,会直接触发 运行时恐慌(panic)。
- 带判断的形式(推荐,避免 panic):
s1, ok := value.(T)
- 第二个返回值
ok是bool类型:- 若断言成功,
ok为true,第一个返回值是转换后的T类型值。 - 若断言失败,
ok为false,第一个返回值是T类型的零值(不会 panic)。
- 若断言成功,
二、作用
- 检查接口值的动态类型:确认接口变量底层存储的具体类型是否为
T。 - 提取具体值:将接口值转换为具体类型后使用。
三、示例
package main
import "fmt"
func main() {
var x interface{} = "hello"
// 基础形式(成功案例)
s1 := x.(string)
fmt.Println(s1) // 输出:hello
// 带判断的形式(成功案例)
if s2, ok := x.(string); ok {
fmt.Println(s2) // 输出:hello
}
// 带判断的形式(失败案例)
if num, ok := x.(int); ok {
fmt.Println(num)
} else {
fmt.Println("x 不是 int 类型") // 输出:x 不是 int 类型
}
// 基础形式(失败会 panic)
// num := x.(int) // 运行时 panic:interface conversion: interface {} is string, not int
}
四、注意事项
-
只能用于接口类型:
value必须是接口变量,否则编译报错。
var a int = 10 // a.(string) // 编译错误:cannot type assert on non-interface value a (type int)
- 判断接口实现:若
T是接口类型,断言用于检查value的动态类型是否实现了T接口。
type MyInterface interface {
Do()
}
type MyStruct struct{}
func (m MyStruct) Do() {}
func main() {
var x interface{} = MyStruct{}
// 检查 x 的动态类型是否实现了 MyInterface
if v, ok := x.(MyInterface); ok {
v.Do() // 可以调用接口方法
}
}
- 配合
switch类型分支:在switch中可使用.(type)语法(类型开关)批量判断类型:
var x interface{} = 100
switch v := x.(type) {
case int:
fmt.Println("int 类型:", v)
case string:
fmt.Println("string 类型:", v)
default:
fmt.Println("未知类型")
}
// 输出:int 类型: 100
五、总结:
.(T) 是 Go 中处理接口类型的重要语法,用于安全地获取接口底层的具体类型和值,带 ok 的形式可避免运行时恐慌,是实际开发中的首选。