为什么typeof(method)不返回reflect.Method实例?

时间:2019-05-15 06:43:18

标签: go methods reflection types

假设我具有Foo结构,其方法定义如下:

type Foo struct {
    Name string
}

func (f *Foo) Get(a int, b string) (string, error) {
    return f.Name, nil
}

如果我写

obj := &Foo{}
t := reflect.TypeOf(obj.Get)

t.Kind()返回reflect.Func,显然我无法访问Get函数的信息,我将类型信息从“属于”提取到Foo结构,即接收者是Foo类型的,甚至没有出现在参数中。

我想这是有意的,我想念一些有关函数的基本知识,这些函数使语言作者抛弃了接收者信息,而这些信息只是用于方法引用的typeof操作的。

我有两个问题:

  1. 我正确了吗,无法通过上面的TypeOf调用来获取代码片段中的接收者类型吗?
  2. 如果我想将有关方法的反射信息传递给打算分析功能和相关接收者的代码(实质上是方法),我有什么选择?

尝试自己回答第二个问题,根据我在官方文档中看到的内容,看来我唯一的选择是传递TypeOf(receiver)和TypeOf(receiver.method)或TypeOf(receiver)以及名称接收者的方法。

1 个答案:

答案 0 :(得分:5)

如mkopriva所述,您拥有的是method valueobj.Get。方法值是一个函数,其签名与没有接收方类型的方法的签名相同:

  

如果表达式x具有静态类型T,并且M在类型T的{​​{3}}中,则x.M被称为< em>方法值。方法值x.M是一个函数值,可以使用与<{1}} 方法调用相同的自变量来调用。在计算方法值期间对表达式x进行评估并保存;然后,保存的副本将在所有调用中用作接收者,以后可能会执行。

如果使用method set(而不是方法值),则接收器类型将在参数列表中“显示”(始终是第一个):

x.M

输出(在method expression上尝试):

fmt.Println(reflect.TypeOf((*Foo).Get))

方法表达式:

  

如果func(*main.Foo, int, string) (string, error) 在类型M的{​​{3}}中,则T是可以作为常规函数调用的函数,其参数与T.M相同以作为方法的接收者的附加参数作为前缀

查看相关问题:

Go Playground

method set