为了确定给定类型是否使用reflect包实现接口,您需要将reflect.Type传递给reflect.Type.Implements()。你怎么得到这些类型之一?
例如,尝试获取未初始化的os.Error(接口)类型的类型不工作(当你在它上面调用Kind()时会发生恐慌)
var err os.Error
fmt.Printf("%#v\n", reflect.TypeOf(err).Kind())
答案 0 :(得分:26)
这样做:
var err *os.Error
t := reflect.TypeOf(err).Elem()
或者在一行中:
t := reflect.TypeOf((*os.Error)(nil)).Elem()
答案 1 :(得分:6)
即使Shaws的反应是正确的,但是很简短。来自reflect.TypeOf方法文档的更多细节:
// 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))
fmt.Println(fileType.Implements(writerType))
答案 2 :(得分:2)
对于那里的googlers,我只是遇到了可怕的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
)。