go println朔源

1
2
3
4
5
6
7
8
type integer int
func (i integer) String() string {
return "hello"
}
func main() {
fmt.Println(integer(5))
}
//输出 hello;事实上,interger(1),中间数字无论如何变化,输出都是hello

Println—->Fprintln—->p.doPrintln(a)—->p.printArg(arg, 'v')
打断点switch f := arg.(type)发现类型并不走switch,而是调用p.handleMethods(verb),最后调用的是p.fmtString(v.String(), verb)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
switch v := p.arg.(type) {
case error:
handled = true
defer p.catchPanic(p.arg, verb, "Error")
p.fmtString(v.Error(), verb)
return

case Stringer:
handled = true
defer p.catchPanic(p.arg, verb, "String")
p.fmtString(v.String(), verb)
return
}

//另外找到Stringer和error类型定义
type Stringer interface {
String() string
}
type error interface {
Error() string
}

如果自己实现了String方法,那么则会调用你实现的方法,最后输出是hello

1
2
3
4
5
6
7
8
9
10
11
12
13
14
type haha struct{}

func (i *haha) String() string {
return "hello1"
}
func (i *haha) Error() string {
return "hello2"
}
func main() {
fmt.Println(&haha{})
}
//内置的Println是不能输出结构体的,那么走error就会输出我们自己实现的Error方法
[Running] go run "d:\go work\test.go"
hello2

本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议 ,转载请注明出处!