本文講解的實例是從mysql查詢過來的數據如何反射到結構體字段,具體實現方法如下代碼;
代碼目錄:
1129
-common
--common.go //是封裝的代碼
-main.go //是測試代碼
代碼的封裝:
```go
package common
import (
"errors"
"reflect"
"strconv"
"time"
)
//根據結構體中sql標簽映射數據到結構體中并且轉換類型
func DataToStructByTagSql(data map[string]string, obj interface{}) {
objValue := reflect.ValueOf(obj).Elem()
for i := 0; i < objValue.NumField(); i++ {
//獲取sql對應的值
value := data[objValue.Type().Field(i).Tag.Get("sql")]
//獲取對應字段的名稱
name := objValue.Type().Field(i).Name
//獲取對應字段類型
structFieldType := objValue.Field(i).Type()
//獲取變量類型,也可以直接寫"string類型"
val := reflect.ValueOf(value)
var err error
if structFieldType != val.Type() {
//類型轉換
val, err = TypeConversion(value, structFieldType.Name()) //類型轉換
if err != nil {
}
}
//設置類型值
objValue.FieldByName(name).Set(val)
}
}
//類型轉換
func TypeConversion(value string, ntype string) (reflect.Value, error) {
if ntype == "string" {
return reflect.ValueOf(value), nil
} else if ntype == "time.Time" {
t, err := time.ParseInLocation("2006-01-02 15:04:05", value, time.Local)
return reflect.ValueOf(t), err
} else if ntype == "Time" {
t, err := time.ParseInLocation("2006-01-02 15:04:05", value, time.Local)
return reflect.ValueOf(t), err
} else if ntype == "int" {
i, err := strconv.Atoi(value)
return reflect.ValueOf(i), err
} else if ntype == "int8" {
i, err := strconv.ParseInt(value, 10, 64)
return reflect.ValueOf(int8(i)), err
} else if ntype == "int32" {
i, err := strconv.ParseInt(value, 10, 64)
return reflect.ValueOf(int64(i)), err
} else if ntype == "int64" {
i, err := strconv.ParseInt(value, 10, 64)
return reflect.ValueOf(i), err
} else if ntype == "float32" {
i, err := strconv.ParseFloat(value, 64)
return reflect.ValueOf(float32(i)), err
} else if ntype == "float64" {
i, err := strconv.ParseFloat(value, 64)
return reflect.ValueOf(i), err
}
//else if .......增加其他一些類型的轉換
return reflect.ValueOf(value), errors.New("未知的類型:" + ntype)
}
```
代碼的測試:
```go
package main
import (
"fmt"
"github.com/student/1129/common"
)
//Product Product定義一個結構體
type Product struct {
ID int64 `json:"id" sql:"id"`
ProductClass string `json:"ProductClass" sql:"ProductClass"`
ProductName string `json:"ProductName" sql:"productName"`
ProductNum int64 `json:"ProductNum" sql:"productNum"`
ProductImage string `json:"ProductImage" sql:"productImage"`
ProductURL string `json:"ProductUrl" sql:"productUrl" `
}
func main() {
//這塊是模擬mysql獲取單條的數據反射到結構體
data := map[string]string{"id": "1", "ProductClass": "blog", "productName": "5lmh.com", "productNum": "40", "productImage": "http://www.5lmh.com/", "productUrl": "http://www.5lmh.com/"}
productResult := &Product{}
common.DataToStructByTagSql(data, productResult)
fmt.Println(*productResult)
//這塊是模擬mysql獲取所有的數據反射到結構體
Alldata := []map[string]string{
{"id": "1", "ProductClass": "blog", "productName": "5lmh.com", "productNum": "40", "productImage": "http://www.5lmh.com/", "productUrl": "http://www.5lmh.com/"},
{"id": "2", "ProductClass": "blog", "productName": "5lmh.com", "productNum": "40", "productImage": "http://www.5lmh.com/", "productUrl": "http://www.5lmh.com/"},
}
var productArray []*Product
for _, v := range Alldata {
Allproduct := &Product{}
common.DataToStructByTagSql(v, Allproduct)
productArray = append(productArray, Allproduct)
}
for _, vv := range productArray {
fmt.Println(vv)
}
}
```