我正在寻找一种将类型(也许是Reflection.Type?)作为字段保留在自定义结构中的方法。这背后的原因是,我将JSON数组解码为结构,稍后再从中构建SQL查询,但是JSON数组中的int,float和timestamps相同,尽管在查询数据库时它们是不同的。这意味着我需要在查询之前将每个值转换为其正确的类型。
我认为答案就在反射包中,但是我还没有弄清楚如何利用它。
我希望是这样的:
type Column struct {
name string
dataType type
}
someColumn := Column {name: "somecol", dataType: int}
convertedVal := SomeConversionFunc("5", someColumn.dataType)
另外,这种事情也可以工作:
type Column struct {
name string
dataType func()
}
someColumn := Column {name: "somecol", dataType: ConvertToInt}
convertedVal := someColumn.dataType("5")
有任何想法吗?
我尝试使用@evanmcdonnal提供的解决方案,但找不到通用的转换方式float64
(该类型json.Unmarshal
为从json数组解组的任何数字)转换为在数据库中找到的任何数据类型(timestamp
事实证明有点棘手,因为reflect.Value
不会将转换方法导出到time.Time
,这等效于Cassandra的timestamp
)。
所做的工作是使用typeConversion
字段而不是dataType
字段,即持有一个将类型转换为不同列的类型的函数,将json.Unmarshal
变量的类型设置为。
因此,我的结构如下所示:
type Column struct {
name string
typeConversion func(reflect.Value) reflect.Value
}
我已经拥有的一些typeConversion函数如下所示:
func floatToTime(varFloat reflect.Value) reflect.Value {
timestamp := time.Unix(int64(varFloat.Float()), 0)
return reflect.ValueOf(timestamp)
}
func floatToInt(varFloat reflect.Value) reflect.Value {
return reflect.ValueOf(int(varFloat.Float()))
}
实际上,这确实是一个非常好的解决方案,因为它非常通用:该结构定义了构建任何转换函数的方式,这意味着我可以包装任何形式的转换以适合该API,并且返回值始终为reflect.Value
,我可以通过调用来访问具有正确类型的基础值Interface()
,如下所示:
// value is the data unmarshaled by json
// I convert it to reflect.Value, then convert it again using my custom typeConversion
// Then I use Interface() to get the final value in the final (and column-appropriate) type
column.typeConversion(reflect.ValueOf(value)).Interface()
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句