• go语言中结构体tag使用


    go中的tag在结构体中使用的。有两个作用:

    (1)给结构体属性起别名,字段映射。对于不同类型的类型对应不同的值,比如xml,yaml,json等分别对应着不同的区域,当然标签也不同。比如json,bson,都是约定俗成的了。

    (2)做属性判断和验证。

    1.tag中的格式

    (1)tag本身是一个字符串,字符串整个使用反引号``。

    (2)key必须是非空字符串,不能使用双引号。字符串不能包含控制字符,空格,引号,冒号。

    (3)value以双引号标记的字符串

    (4)多个标签之间使用空格连接,标签名不需要使用双引号,标签名对应的值需要使用双引号,多个标签值需要使用逗号连接。

    举例:

    1. type User struct {
    2. UserId int `json:"user_id" bson:"b_user_id,bson_id"`
    3. UserName string `json:"user_name" bson:"b_user_name"`
    4. }

    注意:冒号前后不能有空格。

    比如以下几个就是约定俗成的标签:bson,json,yaml,xml等,当然这个标签是可以自定义的

    2.json,bson标签

    1. type User struct {
    2. ID string `json:"id,omitempty" bson:"_id,omitempty"`
    3. Username string `json:"username,omitempty" bson:"username,omitempty"`
    4. Email string `json:"email,omitempty" bson:"email,omitempty"`
    5. }

    比如以上代码,标签是为了起别名,只是每个标签作用的地方不一样。比如json前后端交互的时候用的多,比如请求和响应的都是json格式的数据。bson在和mongoDB数据库交互的时候使用的多。

    json标签:使用了json标签,用于指定字段在json编码中的名称和行为,在与前端进行数据交互时,使用json标签可以确保字段在序列化为 JSON 数据时具有正确的名称和行为。

    bson标签:使用了bson标签,bson标签是用于指定字段在 MongoDB 数据库中的名称和行为。当使用 MongoDB 数据库进行数据存储时,使用 bson标签可以确保字段在序列化和反序列化 BSON(Binary JSON)数据时具有正确的名称和行为。 

    通过这些标签为字段起别名,可以在前端和数据库端建立字段映射,确保数据正确的传递和存储。

    1. 1. JSON 标签( json ):
    2. - 在结构体字段上使用 json:"field_name" 标签,可以指定字段在 JSON 编码和解码中的别名和选项。
    3. - 例如: UserName string json:"user_name"
    4. - 这样的标签可以指定在 JSON 编码和解码中使用 "user_name" 作为字段的别名。
    5. 2. BSON 标签( bson ):
    6. - 在结构体字段上使用 bson:"field_name" 标签,可以指定字段在 BSON 编码和解码中的别名和选项。
    7. - 例如: UserName string bson:"b_user_name"
    8. - 这样的标签可以指定在 BSON 编码和解码中使用 "b_user_name" 作为字段的别名。
    9. 3. YAML 标签( yaml ):
    10. - 在结构体字段上使用 yaml:"field_name" 标签,可以指定字段在 YAML 编码和解码中的别名和选项。
    11. - 例如: UserName string yaml:"user_name"
    12. - 这样的标签可以指定在 YAML 编码和解码中使用 "user_name" 作为字段的别名。
    13. 4. XML 标签( xml ):
    14. - 在结构体字段上使用 xml:"field_name" 标签,可以指定字段在 XML 编码和解码中的别名和选项。
    15. - 例如: UserName string xml:"user_name"
    16. - 这样的标签可以指定在 XML 编码和解码中使用 "user_name" 作为字段的别名。
    17. 需要注意的是,这些标签的具体含义和使用方式可能因使用的库或工具而有所不同。这些示例展示了在 Go 语言中使用不同标签的一般用法,但具体的实现可能会因库或工具的不同而有所区别。
    18. 至于 YAML 和 XML 文件的读取,可以使用相应的库进行解析和处理。对于 YAML 文件,可以使用 gopkg.in/yaml.v2 包,对于 XML 文件,可以使用 encoding/xml 包或其他第三方包进行解析和处理。

    3.举例

    其实自己也可以想例子,以下案例作参考。

    1. type Student struct {
    2. // 返回给前端的话,首字母大写很奇怪,所以给Name起了个别名
    3. Name string `json:"name"`
    4. Age int
    5. }
    6. func testTag() {
    7. s1 := Student{
    8. Name: "s1k",
    9. }
    10. bytes, err := json.Marshal(s1)
    11. if err != nil {
    12. panic(err)
    13. }
    14. // 将[]byte数组转换为string类型json类型
    15. //s := string(bytes)
    16. var s Student
    17. json.Unmarshal(bytes, &s)
    18. fmt.Printf("%v", s)
    19. }
    20. type User struct {
    21. UserId int `json:"user_id" bson:"b_user_id"`
    22. UserName string `json:"user_name" bson:"b_user_name"`
    23. }
    24. func testJson() {
    25. u := &User{
    26. UserId: 1,
    27. UserName: "tony",
    28. }
    29. fmt.Printf("%T", u)
    30. bytes, _ := json.Marshal(u)
    31. fmt.Println(string(bytes))
    32. // 通过反射获取标签的值
    33. // reflect.TypeOf(u),获取的是指针类型
    34. types := reflect.TypeOf(u)
    35. field := types.Elem().Field(0)
    36. fmt.Println(field.Tag.Get("json"))
    37. fmt.Println(field.Tag.Get("bson"))
    38. }
    39. type Http struct {
    40. Port string `yaml:"port"`
    41. Secret string `yaml:"secretKey"`
    42. Domain string `yaml:"domain"`
    43. }
    44. type Config struct {
    45. Http `yaml:"http"`
    46. }
    47. func testYaml() {
    48. //var h Http
    49. config := new(Config)
    50. file, err := ioutil.ReadFile("config.yaml")
    51. if err != nil {
    52. fmt.Println(err.Error())
    53. }
    54. // 将解析后的数据存储到结构体中
    55. err = yaml.Unmarshal(file, config)
    56. if err != nil {
    57. fmt.Println(err.Error())
    58. }
    59. fmt.Println(config.Http, " ", config.Port, " ", config.Secret, " ", config.Domain)
    60. }
    61. type Person struct {
    62. Name string `json:"name"`
    63. Age string `json:"age,omitempty"` //有 omitempty 属性,因此 encoding/json 在将对象转化 json 字符串时,
    64. // 只要发现对象里的 Addr 为 false, 0, 空指针,空接口,空数组,空切片,空映射,空字符串中的一种,就会被忽略。
    65. }
    66. func testTags() {
    67. p1 := &Person{
    68. Name: "zhangsan",
    69. }
    70. // 所以空字符串就会被忽略
    71. bytes, _ := json.Marshal(p1)
    72. fmt.Printf("%s", bytes)
    73. fmt.Println(p1)
    74. fmt.Printf("%T", p1)
    75. p2 := &Person{
    76. Name: "lisi",
    77. Age: "15",
    78. }
    79. fmt.Println(p2)
    80. }
    81. // 从结构体中取出tag,通过反射
    82. /*
    83. 获取字段 field
    84. 获取标签 tag
    85. 获取键值对 key:value
    86. // 三种获取 field
    87. field := reflect.TypeOf(obj).FieldByName("Name")
    88. field := reflect.ValueOf(obj).Type().Field(i) // i 表示第几个字段
    89. field := reflect.ValueOf(&obj).Elem().Type().Field(i) // i 表示第几个字段
    90. // 获取 Tag
    91. tag := field.Tag
    92. // 获取键值对
    93. labelValue := tag.Get("label")
    94. labelValue,ok := tag.Lookup("label")
    95. */
    96. func getTag() {
    97. p2 := &Person{
    98. Name: "lisi",
    99. Age: "15",
    100. }
    101. // 三种方式获取Field
    102. field := reflect.ValueOf(p2).Elem().Type().Field(1)
    103. getName := field.Tag.Get("json")
    104. // 获取tag
    105. //value, ok := tag.Lookup("name")
    106. fmt.Println(getName)
    107. }

  • 相关阅读:
    [附源码]计算机毕业设计农村人居环境治理监管系统Springboot程序
    『 基础算法题解 』之双指针(上)
    【实战】SpringBoot对接外部API并一步一步性能调优
    通过pyserial操作串口
    计算机考研自命题(1)
    【ASP.NET Core】标记帮助器——替换元素名称
    用go实现cors中间件
    采购组件修改申请办理流程
    Vmware tools安装(已解决VMware和win鼠标不能自由切换问题)
    PaddleOCR学习笔记2-初步识别服务
  • 原文地址:https://blog.csdn.net/Sunshineoe/article/details/133670470