为了确定给定类型是否使用reflect包实现了接口,您需要将reflect.Type传递给reflect.Type.Implements()。 如何获得其中一种类型?
举个例子,尝试获取未初始化的
error
(接口)类型确实不起作用(当你对其调用 Kind() 时它会出现恐慌)
var err error
fmt.Printf("%#v\n", reflect.TypeOf(err).Kind())
var err error
t := reflect.TypeOf(&err).Elem()
或者一行:
t := reflect.TypeOf((*error)(nil)).Elem()
// As interface types are only used for static typing, a common idiom to find
// the reflection Type for an interface type Foo is to use a *Foo value.
writerType := reflect.TypeOf((*io.Writer)(nil)).Elem()
fileType := reflect.TypeOf((*os.File)(nil)).Elem()
fmt.Println(fileType.Implements(writerType))
reflect.TypeFor
函数来获取
reflect.Type
值:
func main() {
errorType := reflect.TypeFor[error]()
err := errors.New("foo")
println(reflect.TypeOf(err).Implements(errorType))
}
scannable dest type interface {} with >1 columns (XX) in result
错误。埃文·肖的回答对我不起作用。这是我解决问题的方法。 我也在使用
lann/squirrel
库,但你可以轻松地将其取出。解决方案实际上并不那么复杂,只需知道要进行的反射调用的神奇组合即可。
me.GetSqlx()
函数只是返回一个实例到
*sqlx.DB
func (me *CommonRepo) Get(query sq.SelectBuilder, dest interface{}) error {
sqlst, args, err := query.ToSql()
if err != nil {
return err
}
// Do some reflection magic so that Sqlx doesn't hork on interface{}
v := reflect.ValueOf(dest)
return me.GetSqlx().Get(v.Interface(), sqlst, args...)
}
func (me *CommonRepo) Select(query sq.SelectBuilder, dest interface{}) error {
sqlst, args, err := query.ToSql()
if err != nil {
return err
}
// Do some reflection magic so that Sqlx doesn't hork on interface{}
v := reflect.ValueOf(dest)
return me.GetSqlx().Select(v.Interface(), sqlst, args...)
}
然后要调用它,您可以执行以下操作:
func (me *myCustomerRepo) Get(query sq.SelectBuilder) (rec Customer, err error) {
err = me.CommonRepo.Get(query, &rec)
return
}
func (me *myCustomerRepo) Select(query sq.SelectBuilder) (recs []Customer, err error) {
err = me.CommonRepo.Select(query, &recs)
return
}
这允许您在各处拥有强类型,但将所有通用逻辑集中在一个地方(在本例中为
CommonRepo
)。