Go 语言类型转换
类型转换用于将一种数据类型的变量转换为另外一种类型的变量。
Go 语言类型转换基本格式如下:
type_name(expression)
type_name 为类型,expression 为表达式。
将整型转换为浮点型:
var a int = 10
var b float64 = float64(a)
将字符串变量 str 转换为整型变量 num
var str string = "10"
var num int
num, _ = strconv.Atoi(str)
注意,strconv.Atoi 函数返回两个值,第一个是转换后的整型值,第二个是可能发生的错误,我们可以使用空白标识符 _ 来忽略这个错误。
将整数转换为字符串
package main
import (
"fmt"
"strconv"
)
func main() {
num := 123
str := strconv.Itoa(num)
fmt.Printf("整数 %d 转换为字符串为:'%s'\n", num, str)
}
将字符串转换为浮点数
package main
import (
"fmt"
"strconv"
)
func main() {
str := "3.14"
num, err := strconv.ParseFloat(str, 64)
if err != nil {
fmt.Println("转换错误:", err)
} else {
fmt.Printf("字符串 '%s' 转为浮点型为:%f\n", str, num)
}
}
输出
字符串 '3.14' 转为浮点型为:3.140000
接口类型转换
接口类型转换有两种情况:类型断言和类型转换。
类型断言
想要判断空接口中的值这个时候就可以使用类型断言,其语法格式:
t, ok := i.(T)
其中:
i:表示类型为interface{}的变量
T:表示断言x可能是的类型
该语法返回两个参数,第一个参数是i
转化为T类型后的变量,第二个值是一个布尔值,若为true则表示断言成功,为false则表示断言失败。
package main
import "fmt"
func main() {
var i interface{} = "Hello, World"
str, ok := i.(string)
if ok {
fmt.Printf("'%s' is a string\n", str)
} else {
fmt.Println("conversion failed")
}
}
以上实例中,我们定义了一个接口类型变量 i,并将它赋值为字符串 “Hello, World”。然后,我们使用类型断言将 i 转换为字符串类型,并将转换后的值赋值给变量 str。最后,我们使用 ok 变量检查类型转换是否成功,如果成功,我们打印转换后的字符串;否则,我们打印转换失败的消息。
类型断言原理
类型转换
类型转换用于将一个接口类型的值转换为另一个接口类型,其语法为:
i.(value)
其中:
i 是目标接口类型
value 是要转换的值
在类型转换中,我们必须保证要转换的值和目标接口类型之间是兼容的,否则编译器会报错。
把接口转换为普通的指针类型。例如,尝试把Walker接口转换成*bird类型,
package main
import (
"fmt"
)
// 接口定义
type Flyer interface { // 定义飞行动物接口
Fly()
}
type Walker interface { // 定义行走动物接口
Walk()
}
// 接口实现
type bird struct{} // 定义飞行类型
func (b *bird) Fly() { // 实现飞行动物飞行接口
fmt.Println("bird: fly")
}
func (b *bird) Walk() { // 实现飞行动物行走接口
fmt.Println("bird: walk")
}
// 接口实现
type pig struct{} // 定义行走类型
func (p *pig) Walk() { // 实现行走动物行走接口
fmt.Println("pig: walk")
}
func main() {
p1 := new(pig)
var a Walker = p1
p2 := a.(*bird) // 尝试把Walker接口转换成*bird结构体指针类型
fmt.Printf("p1=%p p2=%p", p1, p2) // 格式化输出指针类型
}
输出
panic: interface conversion: main.Walker is *main.pig, not *main.bird
把Walker类型转换成*bird
类型,将会直接panic报错:在接口转换时,main.Walker
接口内部保存的是*main.pig
,而不是*main.bird
。因此,在接口转换成其他类型时,接口内保存实例对应的类型指针,必须要转换成相对应的类型指针。
func main() {
p1 := new(pig)
var a Walker = p1
p2 := a.(*pig) // 把Walker接口转换成*pig结构体指针类型
fmt.Printf("p1=%p p2=%p", p1, p2) // 格式化输出指针类型
}
//输出
//p1=0x57bb60 p2=0x57bb60