If you’ve been a reader for a while, you may recall back in April when I first talked about variadic functions. Now we’re ready to dig in a bit further to the details of how these mysterious creatures work.
First we’ll see how they work “from the inside”. That is, from the perspective of someone writing a variadic function.
Passing arguments to
...parametersIf
fis variadic with a final parameterpof type ....T, then withinfthe type ofpis equivalent to type[]T. Iffis invoked with no actual arguments forp, the value passed topisnil. Otherwise, the value passed is a new slice of type[]Twith a new underlying array whose successive elements are the actual arguments, which all must be assignable toT. The length and capacity of the slice is therefore the number of arguments bound to p and may differ for each call site.Given the function and calls
func Greeting(prefix string, who ...string) Greeting("nobody") Greeting("hello:", "Joe", "Anna", "Eileen")within
Greeting, who will have the valuenilin the first call, and[]string{"Joe", "Anna", "Eileen"}in the second.
So in other words, from the perspective of the function author, these can be considered functionally equivalent, with identical implementations:
func Greeting(prefix string, who ...string) {
fmt.Printf("%s %s\n", prefix, strings.Join(who, ", "))
}
func Greeting(prefix string, who []string) {
fmt.Printf("%s %s\n", prefix, strings.Join(who, ", "))
}
Whether who is a variadic argument, or an explicit []string, the type of the argument is the same.
The only difference between these two is that the explicit []string type may receive a non-nil, but empty value, whereas the variadic version cannot—it will always receive nil, or a slice with at least one value.
func Greeting(prefix string, who ...string) {
if who == nil {
/* ... what to do when we're greeting nobody? ... */
} else if len(who) == 0 {
/* ... Cannot happen for a variadic input ... */
} else {
fmt.Printf("%s %s\n", prefix, strings.Join(who, ", "))
}
}
Quotes from The Go Programming Language Specification Version of August 2, 2023