Go语言基础之结构体(冬日篇)

共 9324字,需浏览 19分钟

 ·

2023-10-16 02:34

点击上方“ Go语言进阶学习 ”,进行关注

回复“ Go语言 ”即可获赠从入门到进阶共10本电子书

曲终收拨当心画,四弦一声如裂帛。

前言

Hey,大家好呀,我是码农,星期八,这是最后一次了,同样也是Go面向对象的最后一次了。坚持住,一起看看看吧。


结构体继承

说起继承,学过Java,Python的肯定都不陌生,但是Go中,可没有这个东西呐。

那咋办呢???,还是得用结构体来实现。

假装我们都是男孩,喜欢车,那我们就拿车来举例子吧。


车结构体

      
        
          //车
        
      
      
        type Car struct {
      
      
            Brand  string //车品牌
      
      
            CarNum string //车牌号
      
      
            Tyre   int    //轮胎个数
      
      
        }
      
      
        
          
//给车绑定一个方法,说明车的基本信息 func (this *Car) carInfo() { fmt.Printf("品牌:%s,车牌号:%s,轮胎个数:%d\n"this.Brand, this.CarNum, this.Tyre) }


宝马车

      
        
          //宝马车
        
      
      
        type BMWCar struct {
      
      
            //*Car和Car基本没有区别,一个存的是整个结构体,一个存的是结构体地址,用法大同小异
      
      
            *Car //这就表示继承了Car这个结构体
      
      
        }
      
    


比亚迪车

      
        
          //比亚迪车
        
      
      
        type BYDCar struct {
      
      
            *Car
      
      
        }
      
    

可能看到这,你会有种熟悉得感觉,这不就是上节课所将的结构体嵌套吗???

这跟继承有毛关系?

其实在Go中,结构体既可以用来 存储数据 ,也可以 用来模仿对象 的各种操作。

main代码

      
        func main() {
      
      
            //一个宝马对象
      
      
            var bmw1 = BMWCar{&Car{
      
      
                Brand:  "宝马x8"
      
      
                CarNum: "京666"
      
      
                Tyre:   4
      
      
        }}
      
      
            //一个比亚迪对象
      
      
            var byd1 = BYDCar{&Car{
      
      
                Brand:  "比亚迪L3"
      
      
                CarNum: "京111"
      
      
                Tyre:   4
      
      
        }}
      
      
            //因为 BMWCar 和 BYDCar 都继承了Car,所以都有carInfo这个方法
      
      
            bmw1.carInfo()
      
      
            byd1.carInfo()
      
      
        }
      
    

执行结果

b978c0bbec0442a34b129c47b02b9985.webp

这就是一个最简单的,面向对象,跟其他语言一样,继承会将所有的属性和方法都继承过来。


序列化

到此为止呢,结构体基本可以告一段落了,基本算是入门了,当然,并没有结束,但是我想大家都累了,换个方向继续玩。

这个东西叫做序列化,什么意思呢,就是像咱们的 切片 了, map 了, 结构体 了等,这些都是Go的类型。

如果要和其他语言交流,人家可没有这些玩意唉,那怎么办呢???

众多大佬就形成了一个规范, json 数据格式, json 数据必须是 字符串类型

最外面是 ' 号,键/值对组合中的键名写在前面并用双引号 "" 包裹。

就像这样。

      
        '{"Gender":"男""Name":"张三"}'    //'说明这个是字符串,一般打印时不显示
      
    

序列化我们用到的是 json 模块的 Marshal 方法。


切片序列化

单独的切片序列化用的很少,但是仍然还是要知道。

示例代码

      
        package main
      
      
        
          
import ( "encoding/json" "fmt" )
type Student struct { Gender string Name string }
func main() { var StudentList = []string{"张三""李四"} fmt.Printf("StudentList类型:%T\n", StudentList) //[]string,这是列表类型 serializeByte, err := json.Marshal(StudentList) if err != nil { fmt.Println("序列化失败") return } var serializeStr = string(serializeByte) fmt.Printf("serializeStr类型:%T\n", serializeStr) //string,这是字符串类型 fmt.Printf("serializeStr值:%v\n", serializeStr) //["张三","李四"] }

第16行代码将切片序列化,但是返回的是 []byte 类型,第21行代码将 []byte 类型转成字符串。

执行结果

9ca75ba141dca0a0c936de91cde5991f.webp


map序列化

字典序列化,就比较有味道了,序列化的是一个标准的 json 数据格式。

示例代码

      
        package main
      
      
        
          
import ( "encoding/json" "fmt" )
type Student struct { Gender string Name string }
func main() { var StudentInfo = map[string]string{ "Name":"张三" "Age":"18" "Gender":"男" } fmt.Printf("StudentInfo类型:%T\n",StudentInfo) serializeByte, err := json.Marshal(StudentInfo) if err != nil { fmt.Println("序列化失败") } var serializeStr = string(serializeByte) fmt.Printf("serializeStr类型:%T\n", serializeStr) //string,这是字符串类型 fmt.Printf("serializeStr值:%v\n", serializeStr) //{"Age":"18","Gender":"男","Name":"张三"} }

执行结果

5d9f037db7f054b1da55256cc9bcc427.webp

这个就有点像标准的 json 格式了。


结构体序列化

结构体代码

      
        type Student struct {
      
      
            Name   string
      
      
            Gender string
      
      
            Age    int
      
      
        }
      
    

main

      
        func main() {
      
      
          var s1 = Student{
      
      
            Name:   "张三"
      
      
            Gender: "男"
      
      
            Age:    18
      
      
          }
      
      
          fmt.Printf("StudentInfo类型:%T\n", s1)
      
      
          serializeByte, err := json.Marshal(s1)
      
      
          if err != nil {
      
      
            fmt.Println("序列化失败")
      
      
          }
      
      
          var serializeStr = string(serializeByte)
      
      
          fmt.Printf("serializeStr类型:%T\n", serializeStr) //string,这是字符串类型
      
      
          fmt.Printf("serializeStr值:%v\n", serializeStr)
      
      
        }
      
    

执行结果

56a63aaf7f8e3332ea6b0d31cfe02215.webp


切片套结构体

一般情况下,这种方式数据格式是用的比较多的。

当然, 还可以切片嵌套map,方法和此方法一样,不做例子了。

示例代码

      
        package main
      
      
        
          
import ( "encoding/json" "fmt" )
type Student struct { Name string Gender string Age int }
func main() { var s1 = Student{ Name: "张三" Gender: "男" Age: 18 } var s2 = Student{ Name: "李四" Gender: "女" Age: 16 } //一个存放 Student 的列表 var studentList = []Student{s1, s2} fmt.Printf("StudentInfo类型:%T\n", studentList) serializeByte, err := json.Marshal(studentList) //main.Student if err != nil { fmt.Println("序列化失败") } var serializeStr = string(serializeByte) fmt.Printf("serializeStr类型:%T\n", serializeStr) //string,这是字符串类型 fmt.Printf("serializeStr值:%v\n", serializeStr) }

执行结果

f1fbe722cde035b36b0a856f947c0d68.webp


结构体标签(Tag)

Tag 可以理解为结构体的说明,由一对 反引号 包裹起来。

但是一般情况下,Tag在序列化是用的比较多。


结构体代码

      
        type Student struct {
      
      
          Name   string `json:"name"`
      
      
          Gender string `json:"gender"`
      
      
          Age    int    `json:"age"`
      
      
        }
      
    

每个字段后面跟的,就是 Tag ,一定不要把格式搞错啦。

main代码

      
        func main() {
      
      
          var s1 = Student{
      
      
            Name:   "张三"
      
      
            Gender: "男"
      
      
            Age:    18
      
      
          }
      
      
          fmt.Printf("StudentInfo类型:%T\n", s1)
      
      
          serializeByte, err := json.Marshal(s1) //main.Student
      
      
          if err != nil {
      
      
            fmt.Println("序列化失败")
      
      
          }
      
      
          var serializeStr = string(serializeByte)
      
      
          fmt.Printf("serializeStr类型:%T\n", serializeStr) //string,这是字符串类型
      
      
          fmt.Printf("serializeStr值:%v\n", serializeStr)  
      
      
        }
      
    

执行结果

2cf5741e4a437cf80c5e9061613f8e6d.webp

可以发现 key 成小写的了,这就说明一个问题。

在序列化时,如果 结构体 json 这个Tag,序列化时就会以 json Tag为准,如果没有 json Tag,则以 结构体字段为准


总结

上述我们学习了Go基础之结构体的 结构体继承 序列化 结构体标签 。学完Go的结构体,可能你也知道了在Go中是如何模仿面向对象了。

一定记得多多实践,多多敲代码。如果在操作过程中有任何问题,记得下面讨论区留言,我们看到会第一时间解决问题。

我是码农星期八,如果觉得还不错,记得动手点赞一下哈。感谢你的观看。

------------------- End -------------------

往期精彩文章推荐:

b764b83c112d9088a631e2745c73aa96.webp

欢迎大家点赞,留言,转发,转载,感谢大家的相伴与支持

想加入Go学习群请在后台回复【 入群

万水千山总是情,点个【 在看 】行不行

/今日留言主题/

浏览 23
点赞
评论
收藏
分享

手机扫一扫分享

分享
举报
评论
图片
表情
推荐
点赞
评论
收藏
分享

手机扫一扫分享

分享
举报