我想了解为什么下面的代码片段无法编译.将函数接受为可能具有任何返回类型的函数参数的Go方法是什么?
程序包主要func main(){test(a)//错误:无法在测试参数中使用(func()类型的字符串)作为func()接口{}的类型test(b)//错误:不能在测试参数中使用b(func()int类型)作为func()接口{}类型}func a()字符串{返回你好"}func b()int {返回1}func test(x func()interface {}){//一些代码...v:= x()//更多代码...}播放: play.golang/p/CqbuEZGy12
我的解决方案基于沃尔克的答案:
程序包主要进口 ("fmt")func main(){//用匿名函数包装函数a和b//的接口返回类型为空.有了这个//匿名函数,测试的调用签名//无需修改返回即可满足//函数a和b的类型.测试(功能()接口{} {返回a()})测试(功能()接口{} {返回b()})}func a()字符串{返回你好"}func b()int {返回1}func test(x func()interface {}){v:= x()fmt.Println(v)}播放: play.golang/p/waOGBZZwN7
解决方案您对Go新手有一个非常常见的误解:空接口 interface {} 不会 意思是任何类型".确实不是.Go是静态类型的.空的接口 interface {} 是实际的(强类型),例如 string 或 struct {Foo int} 或 interface {Explode()bool} .
这意味着,如果某物的类型为 interface {} ,则它具有该类型,而不是任何类型".
您的功能
func test(x func()接口{})采用一个参数.此参数是一个(无参数函数),它返回特定类型,即 interface {} 类型.您可以将与该签名相匹配的任何函数传递给 test :无参数并返回 interface {} ".您的函数 a 和 b 都不匹配此签名.
如上所述: interface {} 不是"whatever"的神奇缩写,它是一种独特的静态类型.
您必须进行更改,例如到:
func a()接口{} {返回你好"}现在,当您返回不是 interface {} 类型的 string 时,这可能看起来很奇怪.之所以可行,是因为任何类型都可以分配给 interface {} 类型的变量(因为每种类型至少都没有方法:-).
I would like to understand why the code snippet below does not compile. What is the Go way of accepting a function as a function argument that may have any return type?
package main func main() { test(a) // Error: cannot use a (type func() string) as type func() interface {} in argument to test test(b) // Error: cannot use b (type func() int) as type func() interface {} in argument to test } func a() string { return "hello" } func b() int { return 1 } func test(x func() interface{}) { // some code... v := x() // some more code.... }Play: play.golang/p/CqbuEZGy12
My solution based on Volker's answer:
package main import ( "fmt" ) func main() { // Wrap function a and b with an anonymous function // that has an empty interface return type. With this // anonymous function, the call signature of test // can be satisfied without needing to modify the return // type of function a and b. test(func() interface{} { return a() }) test(func() interface{} { return b() }) } func a() string { return "hello" } func b() int { return 1 } func test(x func() interface{}) { v := x() fmt.Println(v) }Play: play.golang/p/waOGBZZwN7
解决方案You tripped over a very common misconception for Go newcomers: The empty interface interface{} does not mean "any type". Really, it does not. Go is statically typed. The empty interface interface {} is an actual (strongly typed type) like e.g. string or struct{Foo int} or interface{Explode() bool}.
That means if something has the type interface{} it has that type and not "any type".
Your function
func test(x func() interface{})takes one parameter. This parameter is a (parameterless function) which returns a specific type, the type interface{}. You can pass any function to test which matches this signature: "No parameters and return interface{}". None of your functions a and b match this signature.
As said above: interface {} is not a magical abbreviation for "whatever",it is a distinct static type.
You have to change e.g. a to:
func a() interface{} { return "hello" }Now this might look strange as you return a string which is not of type interface{}. This works because any type is assignable to variables of type interface{} (as every type has at least no methods :-).
更多推荐
空接口返回类型的参数中的接受函数
发布评论