Eine ausführliche Diskussion einiger Schlüsselkonzepte und der Verwendung von Go-Methodenzeigern

PHPz
Freigeben: 2023-04-25 13:55:33
Original
561 Leute haben es durchsucht

In der Go-Sprache ist eine Methode eine Funktion, die an einen bestimmten Typ gebunden ist und über eine Instanz dieses Typs aufgerufen werden kann. Go kann Methoden für jeden Typ definieren, einschließlich benutzerdefinierter Typen (Strukturen, Schnittstellen) und integrierter Typen (Strings, Arrays usw.) und sogar Zeigertypen.

In Go ist der Zeiger auch ein Typ. Der Zeigertyp kann auf jeden Variablentyp verweisen, und der Wert der Variablen kann über den Zeiger geändert werden. Daher können in Go Methoden auch auf Zeigertypen definiert werden.

Im Folgenden besprechen wir ausführlich einige Schlüsselkonzepte und die Verwendung von Go-Methodenzeigern.

Werttypen und Zeigertypen

Sehen wir uns zunächst ein Beispiel zur Definition einer Person-Struktur an: Person 结构体:

type Person struct {
    Name string
    Age  int
}
Nach dem Login kopieren

现在我们可以定义一个接受 Person 类型参数的方法:

func (p Person) ChangeName(name string) {
    p.Name = name
}
Nach dem Login kopieren

注意,这里的 pPerson 类型的值,而不是指针。因此,当我们调用上述方法时,会创建一个新的 Person 值,而修改不会影响原始变量。

person := Person{Name: "张三", Age: 20}
person.ChangeName("李四")
fmt.Println(person.Name) // 输出 "张三"
Nach dem Login kopieren

为了避免这种情况,我们可以定义一个接受 Person 指针类型的方法,这样在方法内部修改 Person 变量时,不会创建一个新的 Person 变量,而是直接修改原始的 Person 变量。

func (p *Person) ChangeName(name string) {
    p.Name = name
}

person := &Person{Name: "张三", Age: 20}
person.ChangeName("李四")
fmt.Println(person.Name) // 输出 "李四"
Nach dem Login kopieren

可以看到,当我们将 person 定义为指向 Person 类型的指针变量,并使用指针类型的方法 ChangeName() 修改 Name 属性时,原始的 Person 变量的 Name 属性会被修改。

指针方法和值方法的区别

在 Go 语言中,除了上述的修改变量值的能力之外,值方法和指针方法还有另外几个区别。

首先,指针方法可以修改接收者(类型本身),而值方法不能。

type Counter struct {
    count int
}

func (c *Counter) Add() {
    c.count++
}

func (c Counter) Get() int {
    return c.count
}

counter := Counter{count: 0}
counter.Add()
fmt.Println(counter.Get()) // 输出 1
Nach dem Login kopieren

在上述代码中,Add() 方法是一个指针方法,用于增加计数器的值,而 Get() 方法是一个值方法,用于获取计数器的值。可以看到,在代码中,我们首先调用了 Add() 方法增加计数器的值,然后再通过 Get() 方法获取计数器的值。

另一个区别是在使用指针类型作为接收者时,可以避免在复制类型时发生内存分配,从而可以提高程序的性能。

func (p *Person) ChangeAge(age int) {
    p.Age = age
}

person := &Person{Name: "张三", Age: 20}
person.ChangeAge(21)
Nach dem Login kopieren

在上述代码中,ChangeAge() 方法是一个指针方法,用于修改 Person 变量的 Age 属性。由于 Person 是一个结构体类型,因此在每次传递值类型的变量时会发生内存分配。但是,如果将 ChangeAge() 方法定义为指针方法,则可以避免发生内存分配。

非指针类型调用指针类型方法

在 Go 语言中,如果一个方法定义在指针类型上,但我们使用非指针类型调用该方法,编译器会自动转换为指针类型调用。

func (p *Person) ChangeName(name string) {
    p.Name = name
}

person := Person{Name: "张三", Age: 20}
person.ChangeName("李四")
fmt.Println(person.Name) // 输出 "李四"
Nach dem Login kopieren

在上述代码中,我们将 person 定义为值类型的变量,但是通过 ChangeName() 方法来修改变量的值。在这种情况下,编译器会自动将 person 转换为指针类型,并调用 ChangeName()rrreee

Jetzt können wir eine Methode definieren, die Parameter vom Typ Person akzeptiert:

rrreee

Beachten Sie, dass p hier ein Wert vom Typ Person ist, kein Zeiger. Wenn wir also die obige Methode aufrufen, wird ein neuer Person-Wert erstellt und die Änderung hat keinen Einfluss auf die ursprüngliche Variable.

rrreee

Um diese Situation zu vermeiden, können wir eine Methode definieren, die den Zeigertyp Person akzeptiert, sodass eine neue Variable erstellt wird, wenn die Variable Person innerhalb der Methode geändert wird nicht erstellt werden. code>Person-Variable, sondern die ursprüngliche Person-Variable direkt ändern. 🎜rrreee🎜Sie können das sehen, wenn wir person als Zeigervariable definieren, die auf den Typ Person zeigt, und die Zeigertypmethode ChangeName()verwenden > Wenn die Eigenschaft Name geändert wird, wird auch die Eigenschaft Name der ursprünglichen Variablen Person geändert. 🎜🎜Der Unterschied zwischen Zeigermethoden und Wertmethoden🎜🎜In der Go-Sprache gibt es neben der oben erwähnten Möglichkeit, Variablenwerte zu ändern, mehrere weitere Unterschiede zwischen Wertmethoden und Zeigermethoden. 🎜🎜Zuallererst können Zeigermethoden den Empfänger (den Typ selbst) ändern, Wertmethoden hingegen nicht. 🎜rrreee🎜Im obigen Code ist die Methode Add() eine Zeigermethode, die zum Erhöhen des Werts des Zählers verwendet wird, während die Methode Get() eine Wertmethode ist used Ermittelt den Zählerwert. Wie Sie sehen können, rufen wir im Code zunächst die Methode Add() auf, um den Zählerwert zu erhöhen, und erhalten dann den Zählerwert über die Methode Get(). 🎜🎜Ein weiterer Unterschied besteht darin, dass bei Verwendung eines Zeigertyps als Empfänger die Speicherzuweisung beim Kopieren des Typs vermieden werden kann, was die Leistung des Programms verbessern kann. 🎜rrreee🎜Im obigen Code ist die Methode ChangeAge() eine Zeigermethode, die zum Ändern der Eigenschaft Age der Variablen Person verwendet wird. Da es sich bei Person um einen Strukturtyp handelt, erfolgt die Speicherzuweisung jedes Mal, wenn eine Variable vom Typ Wert übergeben wird. Wenn Sie jedoch die Methode ChangeAge() als Zeigermethode definieren, können Sie die Speicherzuweisung vermeiden. 🎜🎜Zeigertypmethoden von Nicht-Zeigertypen aufrufen🎜🎜Wenn in der Go-Sprache eine Methode für einen Zeigertyp definiert ist, wir die Methode jedoch mit einem Nicht-Zeigertyp aufrufen, konvertiert der Compiler sie automatisch in einen Zeigertyp Anruf. 🎜rrreee🎜Im obigen Code definieren wir person als Variable vom Werttyp, ändern aber den Wert der Variablen über die Methode ChangeName(). In diesem Fall konvertiert der Compiler person automatisch in einen Zeigertyp und ruft die Methode ChangeName() auf. 🎜🎜Zusammenfassung🎜🎜In der Go-Sprache ist die Verwendung von Zeigertypen und -methoden sehr verbreitet. Durch die Erstellung einer neuen Zeigertypmethode können wir die Speicherzuweisung beim Kopieren des Typs vermeiden. Gleichzeitig können Zeigermethoden auch den Empfänger ändern. Darüber hinaus konvertiert der Compiler beim Aufrufen einer Zeigertypmethode unter Verwendung eines Nicht-Zeigertyps den Aufruf automatisch in einen Zeigertyp. Daher wird beim Schreiben von Go-Code empfohlen, Zeigertypen und -methoden flexibel zu verwenden, um eine bessere Leistung und Programmstruktur zu erzielen. 🎜

Das obige ist der detaillierte Inhalt vonEine ausführliche Diskussion einiger Schlüsselkonzepte und der Verwendung von Go-Methodenzeigern. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Quelle:php.cn
Erklärung dieser Website
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn
Beliebte Tutorials
Mehr>
Neueste Downloads
Mehr>
Web-Effekte
Quellcode der Website
Website-Materialien
Frontend-Vorlage
Über uns Haftungsausschluss Sitemap
Chinesische PHP-Website:Online-PHP-Schulung für das Gemeinwohl,Helfen Sie PHP-Lernenden, sich schnell weiterzuentwickeln!