Home >Backend Development >Golang >What is the difference between methods and functions in go language

What is the difference between methods and functions in go language

青灯夜游
青灯夜游Original
2023-01-03 11:23:395419browse

Difference: 1. Function is a piece of code with independent functions, which can be called repeatedly many times to achieve code reuse; while method is the behavioral function of a class and can only be called by objects of that class. . 2. Methods have receivers, but functions have no receivers. 3. Functions cannot have the same name, but methods can have the same name. 4. The calling methods are different. 5. The method needs to specify its type, which can be a structure or a custom type, while functions are universal. 6. The form and parameter type of the function must be consistent, and the method can be changed.

What is the difference between methods and functions in go language

The operating environment of this tutorial: Windows 7 system, GO version 1.18, Dell G3 computer.

In the Go language, functions and methods are different and have clear conceptual distinctions. In other languages, such as Java, generally speaking, a function is a method, and a method is a function. However, in the Go language, a function refers to a method that does not belong to any structure or type. In other words, a function has no receiver; Methods have receivers. The methods we are talking about either belong to a structure or belong to a newly defined type.

Function

Function and method, although the concepts are different, the definitions are very similar. The function definition statement has no receiver, so we can define the statement directly in the go file and under the go package.

func main() {
    sum := add(1, 2)
    fmt.Println(sum)
}

func add(a, b int) int {
    return a + b
}

In the example, we defined add as a function, its function signature is func add(a, b int) int, there is no receiver, directly It is defined under a package of go and can be called directly. For example, the main function in the example calls the add function.

The function name in the example starts with lowercase add, so its scope only belongs to the declared package and cannot be used by other packages. If we change the function name to Starting with a capital letter, the scope of the function is large and can be called by other packages. This is also the use of upper and lower case in the Go language. For example, in Java, there are special keywords to declare the scope private, protect, public, etc.

/*
 提供的常用库,有一些常用的方法,方便使用
*/
package lib

// 一个加法实现
// 返回a+b的值
func Add(a, b int) int {
    return a + b
}

The Add method defined in the above example can be called by other packages.

Method

The declaration of method is similar to that of function. The difference is that when the method is defined, it will be placed between func and the method name. Add a parameter, this parameter is the receiver, so that the method we define is bound to the receiver, and is called the method of the receiver.

type person struct {
    name string
}

func (p person) String() string{
    return "the person name is "+p.name
}

In the example, pay attention to the parameter (p person) added between func and the method name. This is the receiver. Now we say that type person has a String method, now let's see how to use it.

func main() {
    p:=person{name:"张三"}
    fmt.Println(p.String())
}

The calling method is very simple. Just use the type variable to call. The type variable and method are preceded by a . operator, which indicates that a certain method of this type variable is to be called. mean.

There are two types of receivers in the Go language: value receivers and pointer receivers. In our above example, we are using a value type receiver.

Using the method defined by the value type receiver, when called, actually uses a copy of the value receiver, so any operation on the value will not affect the original type variable.

func main() {
    p:=person{name:"张三"}
    p.modify() //值接收者,修改无效
    fmt.Println(p.String())
}

type person struct {
    name string
}

func (p person) String() string{
    return "the person name is "+p.name
}

func (p person) modify(){
    p.name = "李四"
}

In the above example, the printed value is still 张三, and modifications to it are invalid. If we use a pointer as the receiver, it will work, because the pointer receiver passes a copy of the pointer to the original value. The copy of the pointer still points to the value of the original type, so when it is modified, it will also Affects the value of the original type variable.

func main() {
    p:=person{name:"张三"}
    p.modify() //指针接收者,修改有效
    fmt.Println(p.String())
}

type person struct {
    name string
}

func (p person) String() string{
    return "the person name is "+p.name
}

func (p *person) modify(){
    p.name = "李四"
}

You only need to change it and become the receiver of the pointer, and the modification is completed.

When calling a method, the receivers passed are essentially copies, but one is a copy of the value, and the other is a copy of the pointer pointing to the value. The pointer has the characteristic of pointing to the original value, so modifying the value pointed by the pointer also modifies the original value. We can simply understand that the value receiver uses a copy of the value to call the method, while the pointer receiver uses the actual value to call the method.

In the above example, did you find that when we call the pointer receiver method, we also use a value variable, not a pointer. It is also possible if we use the following .

p:=person{name:"张三"}
(&p).modify() //指针接收者,修改有效

This is also possible. If we do not force the use of pointers for calls, the Go compiler will automatically help us get the pointers to meet the receiver's requirements.

Similarly, if it is a method of a value receiver, it can also be called using a pointer. The Go compiler will automatically dereference to meet the requirements of the receiver, such as String( defined in the example ) method can also be called like this:

p:=person{name:"张三"}
fmt.Println((&p).String())

In short, when calling a method, you can use either a value or a pointer. We don’t need to strictly abide by these. The Go language compiler will help us. Automatically escaped, which greatly facilitates us developers.

不管是使用值接收者,还是指针接收者,一定要搞清楚类型的本质:对类型进行操作的时候,是要改变当前值,还是要创建一个新值进行返回?这些就可以决定我们是采用值传递,还是指针传递。

Go语言中方法和函数的区别

1、含义不同

函数function是一段具有独立功能的代码,可以被反复多次调用,从而实现代码复用。而方法method是一个类的行为功能,只有该类的对象才能调用。

2、方法有接受者,而函数无接受者

  • Go语言的方法method是一种作用于特定类型变量的函数,这种特定类型变量叫做Receiver(接受者、接收者、接收器); 

  • 接受者的概念类似于传统面向对象语言中的this或self关键字;

  • Go语言的接受者强调了方法具有作用对象,而函数没有作用对象; 

  • 一个方法就是一个包含了接受者的函数; 

  • Go语言中, 接受者的类型可以是任何类型,不仅仅是结构体, 也可以是struct类型外的其他任何类型。

3、函数不可以重名,而方法可以重名

只要接受者不同,则方法名可以一样。

4、调用方式不一样

方法是struct对象通过.点号+名称来调用,而函数是直接使用名称来调用。

方法的调用需要指定类型变量调用,函数则不需要

 ```
var p testMethod.Person
p.Name = "tom"
p.Age = 123
p.ShowInfo()

注:方法和函数的访问权限都受大小写影响,小写本包,大写全局

5、方法需要指定所属类型,可以是结构体也可以是自定义type,函数则通用

```
func (person Person) ShowInfo(形参) 返回值{

   person.Name = "123"
   person.Age = 12
   fmt.Printf("name=%v,age=%v",person.Name,person.Age)
}
```
 
person为类型的形参,类型为Person

6、函数的形参与传参类型需要一致,方法可以改变

     ```
func (person *Person) ShowInfo(形参) 返回值{

   person.Name = "123"
   person.Age = 12
   fmt.Printf("name=%v,age=%v",person.Name,person.Age)
}

(1)这里方法的类型形参为指针,调用时可以使用 p.ShowInfo()或者 (&p).ShowInfo(),本质上都是后者,只不过Go的设计者对于方法的调用做了底层优化

func (person Person) ShowInfo(形参) 返回值{

   person.Name = "123"
   person.Age = 12
   fmt.Printf("name=%v,age=%v",person.Name,person.Age)
}

(2)这里方法的形参类型为数值型,默认为值传递,而在调用时可以使用p.ShowInfo()或者 (&p).ShowInfo(),但依旧是值拷贝

func test01(i *int) {


}

(3)对于函数则需保持一致,需要的形参为指针,则传入的形参需为地址值,否则编译无法通过

【相关推荐:Go视频教程编程教学

The above is the detailed content of What is the difference between methods and functions in go language. For more information, please follow other related articles on the PHP Chinese website!

Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn