如何使用Golang将结构体的方法作为参数传递给另一个函数

Sorry, I post my question again.

I have been read the solution before I ask my question. I think it can not help me because my question is how to pass a function as a parameter? I don't want to call it.

I just want to pass it to another function that I can't edit (or I don't want to edit), and I want to use a string variable to point the function

funcName := "Go"
 m.set(t.funcName)

I think this is different from this question Call a Struct and its Method by name in Go?

for example

I have a function like:

type Context struct{}
type myclass struct{}
type Handler func (c *Context)

func (r *myclass) set(ch Handler)  {

}

I can use this way:

type testclass struct {}
func (t *testclass) Go(c *Context){
    println("Hello");
}

t := &testclass{}
m := &myclass{}
m.set(t.Go)

and my question is

type testclass struct{}
func (t *testclass) Go(c *Context){
    println("Hello");
}

t := &testclass{}
m := &myclass{}

funcName := "Go"
m.set(t.funcName)

any way can do this?

reflect?or what?

if it is impossible, there are other ways to do this?

thanks

You can get the method by name using the reflect package. Here's a function to get a Handler given the name:

func handlerByName(v interface{}, name string) (Handler, error) {
  m := reflect.ValueOf(v).MethodByName(name)
  if !m.IsValid() {
    return nil, errors.New("method not found")
  }
  h, ok := m.Interface().(func(*Context))
  if !ok {
    return nil, errors.New("method is not a handler")
  }
  return h, nil
}

Here's how to use the function:

h, err := handlerByName(t, "Go")
if err != nil {
   // handle error
}
m.set(h)

playground example

Note that the function returned by handlerByName is a reflection wrapper around the original function (thanks @OneOfOne for pointing this out). Calling the wrapper is slow compared to calling the function directly.