這是一個建立於 的文章,其中的資訊可能已經有所發展或是發生改變。
map映射到結構體,這裡只支援簡單的資料類型,複雜的需要在拓展
package mainimport ("errors""fmt""reflect""strconv""time")type User struct {Name stringAge int8Date time.Time}func main() {data := make(map[string]interface{})data["Name"] = "張三"data["Age"] = 26data["Date"] = "2015-09-29 00:00:00"result := &User{}err := FillStruct(data, result)fmt.Println(err, fmt.Sprintf("%+v", *result))}//用map填充結構func FillStruct(data map[string]interface{}, obj interface{}) error {for k, v := range data {err := SetField(obj, k, v)if err != nil {return err}}return nil}//用map的值替換結構的值func SetField(obj interface{}, name string, value interface{}) error {structValue := reflect.ValueOf(obj).Elem() //結構體屬性值structFieldValue := structValue.FieldByName(name) //結構體單個屬性值if !structFieldValue.IsValid() {return fmt.Errorf("No such field: %s in obj", name)}if !structFieldValue.CanSet() {return fmt.Errorf("Cannot set %s field value", name)}structFieldType := structFieldValue.Type() //結構體的類型val := reflect.ValueOf(value) //map值的反射值var err errorif structFieldType != val.Type() {val, err = TypeConversion(fmt.Sprintf("%v", value), structFieldValue.Type().Name()) //類型轉換if err != nil {return err}}structFieldValue.Set(val)return nil}//類型轉換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)}