Go语言不允许隐式类型转换,所有转换必须显式写出;基础数值类型用T(x)转换但有溢出风险,string与[]byte互转语义不同,跨类转换需strconv包,接口还原须类型断言。

Go 语言不允许隐式类型转换,所有转换都必须显式写出,否则编译直接报错。这不是限制,而是防止意外截断、精度丢失或语义混淆的设计选择。
基础数值类型之间怎么转
同类数值类型(如 int ↔ int64、float64 → int)支持直接用 T(x) 语法转换,但行为有关键差异:
-
int64→int:编译器不检查溢出,运行时若值超出目标类型范围,结果是未定义的(通常是高位截断) -
float64→int:直接截断小数部分,不是四舍五入;-3.9转成int是-3 -
uint↔int:按位复制,负数转uint会得到巨大正数(比如int(-1)→uint(0xffffffff))
string 和 []byte 怎么互转
它们底层都是字节序列,所以 string([]byte) 和 []byte(string) 允许直接转换,但语义和内存行为完全不同:
-
string([]byte):不分配新内存,复用原底层数组(只读视图) -
[]byte(string):一定分配新底层数组,原字符串内容被拷贝一份 - 如果后续要修改
[]byte,又想避免意外影响其他引用,这种拷贝反而是安全的 - 大量重复转换会造成 GC 压力,尤其在循环里 —— 能缓存就缓存,别每次都转
字符串和数字之间怎么转
这类跨类转换不能用 T(x),必须走 strconv 包,因为涉及解析逻辑和错误处理:
立即学习“go语言免费学习笔记(深入)”;
-
string→int:用strconv.Atoi()(十进制)或strconv.ParseInt(s, 10, 64)(可指定进制和位宽) -
int→string:首选strconv.Itoa()(快且简洁),或strconv.FormatInt(int64, 10) -
float64→string:用strconv.FormatFloat(f, 'g', -1, 64),第三个参数控制精度,-1表示自动选择最短表示 - 所有
Parse*函数都返回(value, error),忽略error是常见 panic 来源
接口类型怎么转回具体类型
当变量是 interface{} 或某个接口类型,需要还原为具体类型时,不能用 T(x),得用类型断言:
- 暴力断言:
s := i.(string)—— 如果i不是string,运行时 panic - 安全断言:
s, ok := i.(string)——ok为false时不 panic,可做分支处理 - 多个类型判断用
type switch,比一连串if s, ok := ...更清晰 - 注意:只有接口值持有了具体类型的实例,断言才可能成功;空接口
nil断言任何类型都会失败
最容易被忽略的是:自定义类型(哪怕底层是 int)和它的底层类型互转也必须显式写 MyType(x) 或 int(myVar),编译器不认为它们“相等”。这点在定义 ID、TimeSec 等语义化类型时特别容易踩坑。


















