这两种变体有什么区别?

时间:2017-05-02 13:53:43

标签: go multiple-value

我试着创建自己的代码来学习如何在main函数中返回多个值:

package main

import "fmt"

func main() {
    fmt.Println("Enter a integer:")
    var I int
    fmt.Scanf("%d", &I)
    fmt.Println("Accepted:", I)

    O := half(I)
    fmt.Println("Returned:", O)
}

func half(N int) (int, bool) {
    var NA int
    NA = N / 2
    if NA%2 == 0 {
        fmt.Println("even")
        return NA, true
    } else {
        fmt.Println("odd")
        return NA, false
    }
}

给出错误:half.go|11| multiple-value half() in single-value context。 然而另一种变体正在起作用:

package main

import (
    "fmt"
)

func half(number int) (int, bool) {
    if x := int(number % 2); x == 0 {
        return x, true
    } else {
        return x, false
    }
}

func main() {
    fmt.Println(half(1))
    fmt.Println(half(2))
}

我做错了什么?如何克服我的错误?

2 个答案:

答案 0 :(得分:3)

如果一个函数有2个返回值,你必须“期望”它们两个或根本没有。更多相关信息:Return map like 'ok' in Golang on normal functions

您的half()函数有2个返回值,因此当使用short variable declaration将返回值存储在变量中时,您必须提供2个变量:

O, even := half(I)
fmt.Println("Returned:", O, even)

在第二种情况下,您没有存储返回的值,而是将它们传递给具有签名的fmt.Println()

func Println(a ...interface{}) (n int, err error)

fmt.Println()具有可变参数,因此您可以向其传递任意数量的参数。这里发生的是half()的所有多个返回值都作为Println()的可变参数的值传递。这在Spec: Calls:

中允许并详细说明
  

作为一种特殊情况,如果函数或方法g的返回值在数量上相等并且可以单独分配给另一个函数或方法f的参数,则调用{{1}将f(g(parameters_of_g))的返回值按顺序绑定到f的参数后,将调用gf的调用必须不包含f调用之外的任何参数,g必须至少有一个返回值。如果g具有最终f参数,则会为其分配返回值...,这些值将在分配常规参数后保留。

请注意,执行此操作时,不允许传递/提供额外参数,因此例如以下也是编译时错误

g

查看以下类似问题:

Go: multiple value in single-value context

Avoid nesting from conjunction with function that returns 2 values in go?

答案 1 :(得分:1)

fmt.Println接受任意数量的参数,因此可以接受half的结果。

在第一个中,您需要为两个变量提供场所。之一:

i,b := half(2)

i, _ := half(2)

如果你不需要第二次回归。