1.方法总是绑定对象实例,并且隐式将实例作为第一实参,例如func( receiver) dosomething(){},
- receiver是类型,如果程序需要,前面可以加参数,如果不需要,可以省略
- reveiver可以是P或者*p,但是P必须是基类型,不能是接口或者指针
- 不支持重载
- 可以使用实例来调用全部方法
type Ss string func (f Ss) To() { fmt.Println(f) } func (f *Ss) To2() { fmt.Println(f) } type User struct { id int } func(user User) tellId(){ fmt.Println(user.id) } func (user *User) tellId2(){ fmt.Println((*user).id) } func main() { var s = Ss("sss") s.To() // sss s.To2() // 0xc000084030 var u = User{1} u.tellId() // 1 u.tellId2() // 1 }
这样看来是不是很想python中的类,接下来看一下receiver的p与*p的区别,可以看出*p的地址都是一致的
type Ss string
func (f Ss) ToValue() {
fmt.Printf("value %p ", &f)
}
func (f *Ss) ToPointer() {
fmt.Printf("pointer %p ", f)
}
func main() {
var s = Ss("sss")
s1 := &s
fmt.Printf("main %p ", s1) // main 0xc00009c030
s.ToValue() // value 0xc000084040
s.ToPointer() // pointer 0xc0000661c0
s1.ToValue() // value 0xc000090000
s1.ToPointer() // pointer 0xc0000661c0
}
2.匿名字段
从下面例子中可以看出,通过匿名字段,实现了跟python类似的继承功能,以前说的,编译器的查找顺序,从外到内,如果找到,就会停止往下找
type Person struct { name string } type User struct { id int Person } func (s *Person) print() string { return fmt.Sprintf("Person :%p--%v", s, s) } func (s *User) print() string { return fmt.Sprintf("User: %p--%v", s, s) } func main() { var u = User{id: 1, Person: Person{name: "xiao ming"}} fmt.Println(u.print()) // User: 0xc000098000--&{1 {xiao ming}} fmt.Println(u.Person.print()) // Person :0xc000098008--&{xiao ming} }
3.表达式
go也可以进行函数地址的传递,但是注意对于方法来讲,如果receiver是基类型,那么函数地址的传递就是进行复制,后续的变化不会影响其结果
type Person struct { name string } type User struct { id int Person } func (s User) print() { fmt.Printf("User: %p--%v ", &s, s) } func main() { var u = User{id: 1, Person: Person{name: "xiao ming"}} u.print() // User: 0xc000088000--&{1 {xiao ming}} uPrint := u.print uPrint() // User: 0xc000088000--&{1 {xiao ming}} uExpression := (*User).print uExpression(&u) // User: 0xc000088000--&{1 {xiao ming}} u.id = 2 u.print() // User: 0xc000096000--{2 {xiao ming}} uPrint() // User: 0xc000096040--{1 {xiao ming}} 如果是*User 则 User: 0xc000096080--{2 {xiao ming}} uExpression(&u) // User: 0xc000096080--{2 {xiao ming}} }