您好,欢迎访问一九零五行业门户网

了解学习golang类型断言

下面由golang教程栏目给大家介绍golang类型断言,希望对需要的朋友有所帮助!
在php中有一个 serialize() 函数 可以把数组序列化成字符串进行存储和传输
如果想反序列化这种字符串,在php中只需要一个简单的unserialize() 函数就可以完成了.但是在golang中可就没有这么容易了,非得费个九牛二虎之力,写上不少代码才行。
这时候只想感叹一下,php真的是世界上最好的语言啊!
我就在今天的开发中遇到了这么个问题,需要使用golang去解析php序列化的字符串,在github上找了个解析的包,但是发现解析之后的结果是个interface{}类型。
顿时我就无从下手了,总在想数据实际上是一个map,但是解析后得到一个interface{} , 这让我怎么用啊
感觉需要用类型断言,但又不太会用,遂去社区问一下吧,期望大佬们能给个答案。
实际上确实很管用。
下面贴一下代码:
package mainimport ( "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这个占位符可以显示变量的类型
下面还有个示例:
package mainimport ( "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都可以达到效果,只是写法不同。
后面我又经人介绍,得到了另外一个包,也能达到效果:
package mainimport ( "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) } //fmt.printf("%t\n", decodedres) //type is map[interface{}]interface{} //type assert decodeddata, ok := decodedres.(map[interface{}]interface{}) if !ok { fmt.printf("unexpected type %t\n", decodedres) } fmt.println(decodeddata["name"]) fmt.println(decodeddata["age"]) //fmt.printf("%t\n", decodeddata["friends"]) // type is map[interface{}]interface{} // type assert friendsres, ok := decodeddata["friends"].(map[interface{}]interface{}) if !ok { fmt.printf("unexpected type %t\n", decodeddata["friends"]) } for _,v := range friendsres { //fmt.printf("type: %t, val: %#v\n", v,v) // type is map[interface{}]interface{} friend, ok := v.(map[interface{}]interface{}) if !ok { fmt.printf("unexpected type %t\n", decodeddata["friends"]) } //fmt.printf("type: %t, val: %#v\n", friend,friend) // type is map[interface{}]interface{} fmt.println(friend["name"]) }}
这个包解析出来的所有结果的类型都是map[interface{}]interface{},所以做类型断言的时候可以简单粗暴一些。
以上就是了解学习golang类型断言的详细内容。
其它类似信息

推荐信息