go的方法值和方法表达式

简介: go的方法值和方法表达式

go的方法可分为方法值(method value),和方法表达式(method expression) 2种情况

准备工作

定义一个结构体,并且声明接收者方法

type User struct {
   id   int
   name string
}
func (self User) Test() {
   fmt.Printf("%p,%v\\n", self, self)
}

方法值

直接将方法声明赋值给新变量:

func main() {
   u := User{1, "tioncico"}
   u.Test()
   fun1 := u.Test
   u.name="tioncico2"
   fun1()
   u.Test()
}

输出:

GOROOT=/Users/tioncico/sdk/go1.17 #gosetup
GOPATH=/Users/tioncico/go/pkg/mod #gosetup
/Users/tioncico/sdk/go1.17/bin/go build -o /private/var/folders/08/hkdkrdpn4mbb\_4l5zbvrq0hh0000gp/T/\_\_\_go\_build\_main_go /Users/tioncico/GolandProjects/LearnGoProject/main.go #gosetup
/private/var/folders/08/hkdkrdpn4mbb\_4l5zbvrq0hh0000gp/T/\_\_\_go\_build\_main_go
%!p(main.User={1 tioncico}),{1 tioncico}
%!p(main.User={1 tioncico}),{1 tioncico}
%!p(main.User={1 tioncico2}),{1 tioncico2}

可看出,方法值为值传递方式,更改name后,fun1的数值并没有更改

方法表达式

func main() {
   u := User{1, "tioncico"}
   u.Test()
   fun1 := (User).Test
   u.name="tioncico2"
   fun1(u)
   u.Test()
}

输出:

GOROOT=/Users/tioncico/sdk/go1.17 #gosetup
GOPATH=/Users/tioncico/go/pkg/mod #gosetup
/Users/tioncico/sdk/go1.17/bin/go build -o /private/var/folders/08/hkdkrdpn4mbb\_4l5zbvrq0hh0000gp/T/\_\_\_go\_build\_main_go /Users/tioncico/GolandProjects/LearnGoProject/main.go #gosetup
/private/var/folders/08/hkdkrdpn4mbb\_4l5zbvrq0hh0000gp/T/\_\_\_go\_build\_main_go
%!p(main.User={1 tioncico}),{1 tioncico}
%!p(main.User={1 tioncico2}),{1 tioncico2}
%!p(main.User={1 tioncico2}),{1 tioncico2}

其实可以看出,方法值为 "具体实例的方法",已经存在具体实例,需要通过实例去调用接收者方法,所以不需要额外传入接收者

而方法表达式为:"结构体的方法",需要额外传入结构体进行实际调用

其他

package main
import "fmt"
type User struct {
   id   int
   name string
}
func (self *User) Test() {
   fmt.Printf("%p,%v\\n", self, self)
}
func main() {
   var u *User=nil
   u.Test()  //直接实例调用
   (*User)(nil).Test()  //方法值实例(实例值为nil)调用
   (*User).Test(nil)  //方法表达式,传入实例(实例为nil)调用
}
目录
相关文章
|
1月前
|
存储 安全 Java
【Golang】(4)Go里面的指针如何?函数与方法怎么不一样?带你了解Go不同于其他高级语言的语法
结构体可以存储一组不同类型的数据,是一种符合类型。Go抛弃了类与继承,同时也抛弃了构造方法,刻意弱化了面向对象的功能,Go并非是一个传统OOP的语言,但是Go依旧有着OOP的影子,通过结构体和方法也可以模拟出一个类。
120 1
|
6月前
|
Go C++
Go语言方法与接收者 -《Go语言实战指南》
本文介绍了 Go 语言中方法的相关概念和用法。方法是绑定到特定类型上的函数,包含值接收者和指针接收者两种形式。值接收者不会改变原始数据,而指针接收者可修改原始数据,且在处理大型结构体时性能更优。文章详细对比了方法与普通函数的区别,并说明了选择指针接收者的原因,如修改原始值、提升性能及保持一致性。此外,Go 支持为任意自定义类型定义方法,不仅限于结构体。最后通过表格总结了方法的核心概念和使用场景。
186 34
|
6月前
|
Go 开发者
运算符与表达式 -《Go语言实战指南》
本章全面介绍Go语言中的运算符及其使用方法。内容涵盖算术、赋值、比较、逻辑、位运算符等类型,结合示例解析其功能与应用场景。此外,还详细说明了运算符的优先级与结合性规则,并强调通过括号提升代码可读性。最后指出Go不支持运算符重载,位运算适用于性能优化场景,帮助开发者高效掌握表达式构建技巧。
164 20
go语言编译时常量表达式
【10月更文挑战第20天】
139 3
|
SQL 关系型数据库 MySQL
Go语言项目高效对接SQL数据库:实践技巧与方法
在Go语言项目中,与SQL数据库进行对接是一项基础且重要的任务
252 11
|
大数据 Shell Go
GO方法与自定义类型
本文详细介绍了 Go 语言中的自定义数据类型与方法。不同于传统的面向对象编程语言,Go 通过结构体 (`struct`) 和方法 (`method`) 来扩展自定义类型的功能。文章解释了如何定义结构体、创建方法,并探讨了值接收器与指针接收器的区别及应用场景。此外,还介绍了方法的可见性以及接收器的命名惯例。通过具体示例,帮助读者更好地理解和应用这些概念。
143 2
|
安全 Go C语言
Go常量的定义和使用const,const特性“隐式重复前一个表达式”,以及iota枚举常量的使用
这篇文章介绍了Go语言中使用`const`定义常量的方法,包括常量的特性“隐式重复前一个表达式”,以及如何使用`iota`实现枚举常量的功能。
|
存储 Ubuntu Go
在Ubuntu 16.04上安装Go 1.6的方法
在Ubuntu 16.04上安装Go 1.6的方法
193 1
|
存储 Ubuntu Go
在Ubuntu 18.04上安装Go的方法
在Ubuntu 18.04上安装Go的方法
243 1

热门文章

最新文章