我有一个像字符串一样的“ key1:value1; key2:value2”(带有key:value
的{{1}}模式的字符串)。
现在我希望将此字符串解析为Go结构:
;
在上面的示例中,struct标记定义了字符串中键的名称,并且可以为其相应的值提供一些验证(如果验证失败,则可以设置默认值)。例如,type CustomStruct struct {
KeyName1 string `name:"key1" somevalidation:"xxx"`
KeyName2 int `name:"key2" somevalidation:"yyy"`
}
是一个KeyName2
的值,所以我希望int
可以检查somevalidation
是否满足大于等于30且小于等于100的要求。 / p>
在另一种方法中,我可以为KeyName2
这样的字符串定义另一个结构CustomStruct2
如何有效,优雅地归档这种要求?
答案 0 :(得分:2)
我假设您可以将数据解析到map [string] interface {}。
使用reflect包设置字段。基本功能如下:
// set sets fields in struct pointed to by pv to values in data.
func set(pv interface{}, data map[string]interface{}) {
// pv is assumed to be pointer to a struct
s := reflect.ValueOf(pv).Elem()
// Loop through fields
t := s.Type()
for i := 0; i < t.NumField(); i++ {
// Set field if there's a data value for the field.
f := t.Field(i)
if d, ok := data[f.Tag.Get("name")]; ok {
s.Field(i).Set(reflect.ValueOf(d))
}
}
}
此代码假定数据映射中的值可分配给结构中的相应字段,并且第一个参数是指向结构的指针。如果这些假设不成立,则代码将感到恐慌。您可以通过使用反射包检查类型和可分配性来防止这种情况。