为什么我不能这样做fmt.Sprintf("%d。%d。%d。%d" a ...)? [英] Why can't I do fmt.Sprintf("%d.%d.%d.%d", a...)?
问题描述
我在学习Go,并且被Go游览卡住(exercise-stringer.go: https ://tour.golang.org/methods/7 )。
以下是一些代码:
键入IPAddr [4] byte
// TODO:向IPAddr添加一个String()字符串方法。
func(a IPAddr)String()string {
return fmt.Sprintf(%d。%d。%d。%d,a ...)
}
所以我认为 IPAddr
的内部表示是 [4] byte
,所以扩展运算符工作。但是我得到:
pre $ 不能使用[] string literal(type [] string)as type [] interface {} in参数为fmt.Sprintf
到底是什么?字符串切片也不起作用,这里发生了什么?
$ b 编辑:对不起,我的问题出错了 - 错误与类型
IPAddr
,而不是 []字符串
。我在玩代码,并且粘贴了错误的输出。无论如何,感谢 peterSO 和 0x434D53 关于Go中切片的不变性。那么,这又引发了另一个问题。为什么这样实施?我想你只有一些 Iterable
接口,所以实现它的任何结构都会正常工作。 Sidenote :当我第一次听说Go的时候,这个大胆的陈述编译,但表达。显式的接口实现就是这方面的一个很好的例子,但是显式转换,运算符重载等缺乏让我有90年代的Java感觉。这很让人伤心,因为Go似乎是一种很棒的语言。
Go Tour of Go练习:击球手
使 例如, 不存在 输出: fmt.Stringer
将地址打印为
$ b IPAddr {1,2,3,4}
应打印为1.2.3.4
。
包主
导入fmt
类型IPAddr [4]字节
// TODO:向IPAddr添加一个String()字符串方法。
func main(){
addrs:= map [string] IPAddr {
loopback:{127,0,0,1},
googleDNS :{8,8,8,8},
}
for n,a:= range addrs {
fmt.Printf(%v:%v \ n,n ,a)
}
}
[] string
到 [] interface {}
的隐式转换。请参阅转换 =nofollow> Go编程语言规范。你需要提供一个明确的转换。例如,
包主
导入fmt
类型IPAddr [4] byte
// IPAddr的String()string方法。
func(a IPAddr)String()string {
return fmt.Sprintf(%d。%d。%d。%d,a [0],a [1],a [2 ],a [3])
}
func main(){
addrs:= map [string] IPAddr {
loopback:{127,0 ,0,1},
googleDNS:{8,8,8,8},
}
for n,a:=范围addrs {
fmt.Printf( %v:%v \ n,n,a)
}
}
loopback:127.0.0.1
googleDNS:8.8.8.8
I'm learning Go and I'm stuck with Go tour (exercise-stringer.go: https://tour.golang.org/methods/7).
Here's some code:
type IPAddr [4]byte
// TODO: Add a "String() string" method to IPAddr.
func (a IPAddr) String() string {
return fmt.Sprintf("%d.%d.%d.%d", a...)
}
So I figured the inner representation of IPAddr
is [4]byte
, so spread operator works. But I'm getting:
cannot use []string literal (type []string) as type []interface {} in argument to fmt.Sprintf
What the heck? String slice doesn't work either, what's going on here?
EDIT: Sorry, there's an error in my question - error was about type IPAddr
, not []string
. I was playing with the code and I've pasted wrong output. Anyway, thanks to peterSO and 0x434D53 about invariance of slices in Go.
Well, this raises another question. Why is it implemented in this way? I imagine you'd just have some Iterable
interface, so any struct implementing it would "just work".
Sidenote: when I first heard about Go there was this bold statement "compiled, but expressive". And explicit interface implementation is great example of this, but things like explicit conversion, lack of operator overloading and so on give me "90s Java feel". Which is sad, because Go seems like a great language.
Exercise: Stringers
Make the
IPAddr
type implementfmt.Stringer
to print the address as a dotted quad.For instance,
IPAddr{1, 2, 3, 4}
should print as"1.2.3.4
".package main import "fmt" type IPAddr [4]byte // TODO: Add a "String() string" method to IPAddr. func main() { addrs := map[string]IPAddr{ "loopback": {127, 0, 0, 1}, "googleDNS": {8, 8, 8, 8}, } for n, a := range addrs { fmt.Printf("%v: %v\n", n, a) } }
There is no implicit conversion of []string
to []interface {}
. See Conversions in The Go Programming Language Specification. You need to provide an explicit conversion. For example,
package main
import "fmt"
type IPAddr [4]byte
// A "String() string" method for IPAddr.
func (a IPAddr) String() string {
return fmt.Sprintf("%d.%d.%d.%d", a[0], a[1], a[2], a[3])
}
func main() {
addrs := map[string]IPAddr{
"loopback": {127, 0, 0, 1},
"googleDNS": {8, 8, 8, 8},
}
for n, a := range addrs {
fmt.Printf("%v: %v\n", n, a)
}
}
Output:
loopback: 127.0.0.1
googleDNS: 8.8.8.8
这篇关于为什么我不能这样做fmt.Sprintf("%d。%d。%d。%d" a ...)?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!