方法集与表达式

黎涛note · · 348 次点击 · · 开始浏览    
这是一个创建于 的文章,其中的信息可能已经有所发展或是发生改变。

Golang 表达式 :根据调用者不同,方法分为两种表现形式:

instance.method(args...) ---> <type>.func(instance, args...)  

前者称为 method value,后者 method expression。

两者都可像普通函数那样赋值和传参,区别在于 method value 绑定实例,而 method expression 则须显式传参。

package main

import "fmt"

type User struct {
    id int
    name string
}

type Manager struct {
    User//通过组合实现继承
    title string
}

func (u *User) ToString() string {
    return fmt.Sprintf("User: %p %v\n",u, u)
}

func (m *Manager) ToString() string  {
    return fmt.Sprintf("Manager: %p %v\n",m, m)
}

func (u *User) TestPointer() {
    fmt.Printf("TestPointer %p,%v\n",u, u)
}

func (u User) TestValue(){
    fmt.Printf("TestValue %p,%v\n",&u,u)
}

func main() {
    m := Manager{User{1,"Tom"},"Administrator"}
    fmt.Println(m.ToString())
    fmt.Println(m.User.ToString())
    fmt.Println("---------------------------------")
    u := User{1,"Tom"}
    u.TestValue()//u为{1,"Tom"}
    uValue := u.TestValue//uValue为当前u的方法,复制了u的值
    u.id,u.name = 2,"cat"//改变u的值
    u.TestValue()//u为改变的值
    uValue()//该方法为复制值的方法
    /* out
    TestValue 0xc0000040a8,{1 Tom}
    TestValue 0xc0000040d8,{2 cat}
    TestValue 0xc000004108,{1 Tom}
     */
    fmt.Println("---------------------------------")
    //总结:方法中的对象为值的拷贝,还是地址的传递,与方法本身的声明相关
    //与调用方法传递的类型无关
    //由于*T的方法包含了*T+T的方法所以可以调用
    u1 := User{1,"Tom"}
    fmt.Printf("u1 %p,%v\n",&u1,u1)
    mv := User.TestValue
    mv(u1)//由于方法有一个隐藏的this指针
    //mv中的u1是对主函数中u1的值拷贝,地址并不相同

    mp := (* User).TestPointer
    mp(&u1)//mp中的u1与主函数中u1是同一个内存且地址相同

    mp2 := (* User).TestValue
    mp2(&u1)//mp2中的u1是对主函数中u1的值拷贝,地址并不相同


}


有疑问加站长微信联系(非本文作者)

本文来自:简书

感谢作者:黎涛note

查看原文:方法集与表达式

入群交流(和以上内容无关):加入Go大咖交流群,或添加微信:liuxiaoyan-s 备注:入群;或加QQ群:692541889

348 次点击  
加入收藏 微博
添加一条新回复 (您需要 登录 后才能回复 没有账号 ?)
  • 请尽量让自己的回复能够对别人有帮助
  • 支持 Markdown 格式, **粗体**、~~删除线~~、`单行代码`
  • 支持 @ 本站用户;支持表情(输入 : 提示),见 Emoji cheat sheet
  • 图片支持拖拽、截图粘贴等方式上传