您好我正在尝试类似以下示例的内容。
我作为PHP开发人员的背景(我知道!)让我很难相处。 我已经阅读了反思法则和其他来源,但这是我的头脑。我使用的方法可能是错误的...希望有人可以指出我正确的方向。
以具体方式使用它是因为版本01或02或03来自外部参数,基于此,我需要获取适当的结构并用数据库值填充它。
package V01
type Struct1 struct{
Field1 string
Field2 string
}
type Struct2 struct{
Field1 string
Field2 string
}
package V02
type Struct1 struct{
Field1 string
Field2 string
ExtraField1 string
}
type Struct2 struct{
Field1 string
Field2 string
ExtraField2 string
ExtraField3 string
}
var VStructs = map[string]map[string]interface{}{
"01": map[string]interface{}{
"Struct1": V01.Struct1{},
"Struct2": V01.Struct2{},
},
"02": map[string]interface{}{
"Struct1": V02.Struct1{},
"Struct2": V02.Struct2{},
},
"03" : map[string]interface{}{
"Struct1": V01.Struct1{},
"Struct2": V02.Struct2{},
},
}
// I get the struct fieldnames and so on.
fmt.Printf("%+v\n", VStructs["01"]["Struct1"] )
// I cannot access any of the fields though because it is an interface
fmt.Println( VStructs["01"]["Struct1"].Field1 ) // PANIC!
// Type Switching is not working either since the version can be variable.
s := VStructs["01"]["Struct1"].Field1
switch x := s.(type) {
case reflect.Struct: // PANIC! reflect.Struct (type reflect.Kind) is not a type
fmt.Println("I am an struct")
default:
fmt.Println("I am an no struct")
}
所以也许可以告诉我一个合适的方法。或者也许是一个包装函数来返回正确的结构......此时没有任何线索。
希望很清楚,如果被要求,还会详细说明。
答案 0 :(得分:0)
您无法以这种方式访问地图内的结构,因为可能没有结构。在您的示例中,VStructs["foo"]["bar"].Field1
会是什么?您无法知道它是否真的是地图中的空结构,或者没有任何内容,并且地图访问只返回了该类型的空值。你应该做的是明确的检查:
v, ok := VStructs["01"]["Struct1"]
if !ok {
// Handle the case of the missing struct.
}
// It is also a good practice to check type assertions.
s, ok := v.(V01.Struct1)
if !ok {
// Handle the case when v is not V01.Struct1.
}
f = s.Field1
答案 1 :(得分:0)
好的,因为这个问题可能与golang的使用方式有冲突。
我写了一个包来满足我的需求:
找到包裹根据所选版本(在URL或标题中,无论你喜欢什么),我们检索结构图。我们现在可以选择我们需要的实际结构,设置一些值,最后将其发送回屏幕或将其发送到DB(在我的情况下为gorp)。