• golang 结构体标签 -- struct tag (八)


    结构体标签可以说是 golang 中一个比较有特殊的特性。在讲解 golang 结构体标签之前我们先来看一个结构体标签最常用的场景。有过 web 后端编程的经验的伙伴们应该都会有这样的感受,后端程序处理数据的流程可以抽象为:1、接受前端请求->处理请求->业务数据写入数据库;2、从数据库读取数据->处理业务->向前端返回数据

    在这两个个过程中程序会有两次数据的转换:前端数据(json 数据或者 form 表单)与程序对象结构体的互转,数据库数据(比如 sql 数据)与程序的对象结构体的互转。

    在这里插入图片描述

    在 golang 中我们借助 struct tag,这些转换都会特别简单。我们来看一个例子:

    package main
    
    import (
    	"encoding/json"
    	"net/http"
    )
    
    // json:"param-1" 和 json:"param-2 即为结构体标签,其
    // 要紧跟在结构体属性后面使用反引号 `` 引起来。
    type data struct {
    	Param1 string `json:"param-1"`
    	Param2 int    `json:"param-2"`
    }
    
    func main() {
    	http.HandleFunc("/getjson", func(w http.ResponseWriter, r *http.Request) {
    		w.Header().Set("Content-Type", "application/json")
    		reps, err := json.Marshal(data{Param1: "I am a string", Param2: 2})
    		if err != nil {
    			panic(err)
    		}
    		w.Write([]byte(reps))
    	})
    	http.ListenAndServe("0.0.0.0:18080", nil)
    }
    
    • 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

    使用 go run main.go 启动程序后,在使用 curl 命令在检验结果:

    # curl -i http://127.0.0.1:18080/getjson
    HTTP/1.1 200 OK
    Content-Type: application/json
    Date: Fri, 30 Sep 2022 07:22:17 GMT
    Content-Length: 39
    
    {"param-1":"I am a string","param-2":2}
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    从上面的例子我们看到借助结构体标签我们能很容易的完成 golang 结构体到 json 数据的转换。除了 json 还有很多其他 golang 库可以完成 golang 结构体到其他数据的转换,如:xmlprotocolbuf ;还能用于数据库 orm 相关 beego ormgorm

    reflect.StructTag

    从上面内容我们了解到了使用 golang 结构体标签的方便之处,但是上面我们都是借助各种库来完成数据的转换的。如果这些库不好用,或者我们遇到一套特有的的数据规范第三方库处理不了,我们想自己写一套处理结构体标签的工具,这时候我们就需要掌握 reflect.StructTag,他是专门用于处理结构体标签的,上面提到的各种库底层都会用到 reflect.StructTag

    我们来看一个官方的例子:

    package main
    
    import (
    	"fmt"
    	"reflect"
    )
    
    func main() {
    	type S struct {
    		F string `species:"gopher" color:"blue"`
    	}
    
    	s := S{}
    	st := reflect.TypeOf(s)
    	field := st.Field(0)
    	fmt.Println(field.Tag.Get("color"), field.Tag.Get("species"))
    
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18

    程序运行的输出结果:

    blue gopher
    
    • 1

    reflect.StructTag 非常简单,就包含了两个方法 GetLookup,详细的介绍可以参考官方文档,但是要想写出真正有用的工具还需要全面的掌握 golang reflect ,关于 golang reflect 在后续章节我也会逐步介绍到。

  • 相关阅读:
    巴州阳光志愿者服务协会党支部开展 第十一季“衣旧情深”爱心 活动
    java版工程管理系统Spring Cloud+Spring Boot+Mybatis实现工程管理系统源码
    1.初始cmake
    [记忆化dfs][排序]leetcode1387:将整数按权重排序(medium)
    C++ 类和对象篇(六) 拷贝构造函数
    PHP 通过 Redis 解决并发请求的操作问题
    力扣-字符串-字符的统计
    Vue中Class绑定和style绑定的方式
    DPDK中的cuckoo hash算法
    手撕二叉搜索树
  • 原文地址:https://blog.csdn.net/yjf147369/article/details/127126108