前言:
我在中发布了此实用程序
github.com/icza/gox,请参见
builtinx.Wrap()。
首先,对于您尝试执行的操作,应该使用
fmt.Printf()而不是
fmt.Println()仅按照前者的预期使用并使用格式字符串。
展望未来,默认情况下不支持此操作,因为从Spec:Calls中引用:
作为一种特殊情况,如果一个函数或方法的返回值
g数量相等并且可以分别分配给另一个函数或方法的参数f,则该调用f(g(parameters_of_g))将在按顺序f将返回值绑定g到参数之后调用f。
的调用f除的调用外不得包含任何参数g,并且g必须至少具有一个返回值。如果f具有最终...参数,则分配g常规参数后保留的返回值。
并
fmt.Printf()具有以下特征:
func Printf(format string, a ...interface{}) (n int, err error)fmt.Printf()除了函数调用(调用的返回值)之外,您不能将其他参数传递给其他参数。
请注意,的签名
fmt.Println()为:
func Println(a ...interface{}) (n int, err error)这意味着它
fmt.Println(temp())起作用,并且对于具有至少一个返回值的任何其他函数也是如此,因为带引号的部分的最后一句话允许这样做(
“如果
f具有最终
...参数,则为其分配返回值,将
g其分配给常规参数。“)
但是,通过一些技巧,我们也可以实现您想要的fmt.Printf()
。
请注意,如果
temp()将返回type的值
[]interface{},我们可以...将其用作某些可变参数的值。
这意味着工作:
func main() { fmt.Printf("1: %v, 2: %vn", temp()...)}func temp() []interface{} { return []interface{}{1, 2} }并正确打印(在Go Playground上尝试):
1: 1, 2: 2
因此,我们只需要一个实用函数即可将任何函数的返回值包装到中
[]interface{},因此我们可以将其传递给fmt.Printf()。
这简直是太简单了:
func wrap(vs ...interface{}) []interface{} { return vs}如上文所述(使用
fmt.Println()),我们可以将至少具有1个返回值的任何函数的返回值
wrap()作为其输入参数的值传递。
现在使用此
wrap()功能,请参见以下示例:
func main() { fmt.Printf("1: %vn", wrap(oneInt())...) fmt.Printf("1: %v, 2: %vn", wrap(twoInts())...) fmt.Printf("1: %v, 2: %v, 3: %vn", wrap(threeStrings())...)}func oneInt() int { return 1 }func twoInts() (int, int) { return 1, 2 }func threeStrings() (string, string, string) { return "1", "2", "3" }这可行,并且输出(在Go Playground上尝试):
1: 11: 1, 2: 21: 1, 2: 2, 3: 3



