Go不支持隐式类型转换,所有转换必须显式声明;int与int64被视为不同类型,不可直接赋值;字符串与数字互转须用strconv包;unsafe.Pointer仅用于底层内存重解释;interface{}取值需类型断言。

Go 语言不支持隐式类型转换,所有类型转换都必须显式声明。这是为了防止意外的精度丢失或语义错误,但初学者常因忽略这一点而遇到编译错误或运行时行为异常。
为什么 int 和 int64 不能直接赋值
Go 把不同长度的整数类型(如 int、int32、int64)视为完全不同的类型,即使它们底层都表示整数。编译器不会自动推导“安全转换”,哪怕数值在范围内。
常见错误现象:
cannot use x (type int64) as type int in assignment
- 即使
x的值是100,var y int = x仍会报错 -
int在 64 位系统上通常是int64,但 Go 不保证这点,也不允许依赖该假设 - 跨平台代码中,
int可能是int32(如 32 位 ARM),直接转换可能溢出
字符串和数字互转:用 strconv 而不是强制类型转换
string(65) 得到的是字符 "A"(ASCII 码),不是字符串 "65";反过来,int("123") 是非法语法。数字 ↔ 字符串必须走 strconv 包。
立即学习“go语言免费学习笔记(深入)”;
正确做法:
import "strconv"
s := strconv.Itoa(42) // int → string
i, err := strconv.Atoi("42") // string → int(支持十进制)
i64, err := strconv.ParseInt("42", 10, 64) // 指定进制和位宽
f, err := strconv.ParseFloat("3.14", 64) // string → float64
-
strconv.Itoa只接受int,若你有int64,得用strconv.FormatInt(x, 10) -
ParseInt第二个参数是进制(通常为10),第三个是位宽(64表示输出int64) - 所有
ParseXxx函数都返回(T, error),忽略err是常见 panic 来源
unsafe.Pointer 实现底层类型重解释(慎用)
仅当需要绕过类型系统做内存层面的 reinterpret(比如将 []byte 当作 []uint32 读取),才考虑 unsafe。这不是常规“类型转换”,而是对同一段内存的不同解释。
典型场景:二进制协议解析、高性能序列化
import "unsafe"
b := []byte{1, 0, 0, 0}
u32 := *(*uint32)(unsafe.Pointer(&b[0])) // 将前 4 字节解释为 uint32(小端)
- 必须确保字节数匹配(
uint32占 4 字节,&b[0]必须有至少 4 字节可用) - 字节序需手动处理,上面例子只在小端机器上得到
1;大端需用binary.BigEndian.Uint32(b) -
unsafe代码无法通过go vet安全检查,且可能被未来 Go 版本限制
最易被忽略的一点:接口类型(interface{})不是“万能容器”,它内部存的是具体类型+值。从 interface{} 取回原类型必须用类型断言(v.(T))或类型开关,而不是任何意义上的“转换”。强行断言失败会 panic,生产环境务必配合 ok 形式使用。










