本文摘自php中文网,作者藏色散人,侵删。
下面由golang教程栏目给大家介绍golang类型断言,希望对需要的朋友有所帮助!在php中有一个 serialize() 函数 可以把数组序列化成字符串进行存储和传输
如果想反序列化这种字符串,在php中只需要一个简单的unserialize() 函数就可以完成了.但是在golang中可就没有这么容易了,非得费个九牛二虎之力,写上不少代码才行。
这时候只想感叹一下,php真的是世界上最好的语言啊!
我就在今天的开发中遇到了这么个问题,需要使用golang去解析php序列化的字符串,在github上找了个解析的包,但是发现解析之后的结果是个interface{}类型。
顿时我就无从下手了,总在想数据实际上是一个map,但是解析后得到一个interface{} , 这让我怎么用啊
感觉需要用类型断言,但又不太会用,遂去社区问一下吧,期望大佬们能给个答案。
实际上确实很管用。
下面贴一下代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 | package main
import (
"github.com/yvasiyarov/php_session_decoder/php_serialize"
"fmt"
"log"
)
func main() {
str := `a:3:{s:4: "name" ;s:3: "tom" ;s:3: "age" ;s:2: "23" ;s:7: "friends" ;a:2:{i:0;a:1:{s:4: "name" ;s:5: "jerry" ;}i:1;a:1:{s:4: "name" ;s:4: "jack" ;}}}`
decoder := php_serialize.NewUnSerializer(str)
if result, err := decoder.Decode(); err != nil {
panic(err)
} else {
decodeData, ok := result.(php_serialize.PhpArray)
if !ok {
log.Println(err)
}
name := decodeData[ "name" ]
age := decodeData[ "age" ]
fmt.Println(name, age)
friends, ok := decodeData[ "friends" ].(php_serialize.PhpArray)
if !ok {
log.Println(err)
}
for _,v := range friends {
fmt.Printf( "type:%T, value:%+v\n" , v,v )
friend, ok := v.(php_serialize.PhpArray)
if !ok {
log.Println(err)
}
friendName := friend[ "name" ]
fmt.Println(friendName)
}
}
}
|
可以粗暴的这么理解:一个变量是什么类型,就进行什么类型的断言,断言后,即可得到结果
怎么判断一个变量的类型?
打印出来呀:fmt.Printf("%T", verb)
%T这个占位符可以显示变量的类型
下面还有个示例:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 | package main
import (
"github.com/yvasiyarov/php_session_decoder/php_serialize"
"fmt"
"log"
)
func main() {
str := `a:3:{s:4: "name" ;s:3: "tom" ;s:3: "age" ;s:2: "23" ;s:7: "friends" ;a:2:{i:0;a:1:{s:4: "name" ;s:5: "jerry" ;}i:1;a:1:{s:4: "name" ;s:4: "jack" ;}}}`
decoder := php_serialize.NewUnSerializer(str)
result, err := decoder.Decode()
if err != nil {
panic(err)
}
t := result.(php_serialize.PhpArray)
strVal := php_serialize.PhpValueString(t[ "name" ])
fmt.Println( strVal )
switch t := result.(type) {
default :
fmt.Printf( "unexpected type %T\n" , t)
case php_serialize.PhpArray:
fmt.Println(t)
fmt.Println(t[ "name" ])
fmt.Println(t[ "age" ])
switch f := t[ "friends" ].(type) {
default :
fmt.Printf( "unexpected type %T\n" , t)
case php_serialize.PhpArray:
fmt.Println(f)
fmt.Println(f[0])
fmt.Println(f[1])
}
}
}
|
上面两个demo都可以达到效果,只是写法不同。
后面我又经人介绍,得到了另外一个包,也能达到效果:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 | package main
import (
"fmt"
"log"
"github.com/wulijun/go-php-serialize/phpserialize"
)
func main() {
str := `a:3:{s:4: "name" ;s:3: "tom" ;s:3: "age" ;s:2: "23" ;s:7: "friends" ;a:2:{i:0;a:1:{s:4: "name" ;s:5: "jerry" ;}i:1;a:1:{s:4: "name" ;s:4: "jack" ;}}}`
decodedRes, err := phpserialize.Decode(str)
if err != nil {
panic(err)
}
decodedData, ok := decodedRes.(map[ interface {}] interface {})
if !ok {
fmt.Printf( "unexpected type %T\n" , decodedRes)
}
fmt.Println(decodedData[ "name" ])
fmt.Println(decodedData[ "age" ])
friendsRes, ok := decodedData[ "friends" ].(map[ interface {}] interface {})
if !ok {
fmt.Printf( "unexpected type %T\n" , decodedData[ "friends" ])
}
for _,v := range friendsRes {
friend, ok := v.(map[ interface {}] interface {})
if !ok {
fmt.Printf( "unexpected type %T\n" , decodedData[ "friends" ])
}
fmt.Println(friend[ "name" ])
}
}
|
这个包解析出来的所有结果的类型都是map[interface{}]interface{},所以做类型断言的时候可以简单粗暴一些。
以上就是了解学习golang类型断言的详细内容,更多文章请关注木庄网络博客!!
相关阅读 >>
docker 概述
go开源说第四期:go-zero解读与最佳实践(上)
如何通过go语言将utc和gmt时间处理为标准北京时间?
go在迅雷p2p连通系统中的性能优化实践-朱文
golang (v2)分布式id生成系统,高性能、高可用、易扩展的id生成服务
golang 断言是什么
手撸golang 基本数据结构与算法 网页排名/pagerank,随机游走
golang判断文件是否能写入的方法
windows下如何玩转火热的go-zero
golang 管道线程安全吗
更多相关阅读请进入《golang》频道 >>
老貘
一个与时俱进的Go编程知识库。
转载请注明出处:木庄网络博客 » 了解学习golang类型断言