En Go, un pointeur est une variable qui contient l'adresse d'une autre variable. Contrairement à certains langages, en Go, il est impossible d'effectuer des opérations arithmétiques sur les pointeurs, ce qui les rend plus sûrs. Les pointeurs en Go sont souvent utilisés pour :
En Go, il n'y a pas de prise en charge explicite des types de références, comme en C++, mais les slices et les maps sont déjà référentiels par nature, et ils sont souvent passés par valeur.
package main import "fmt" type User struct { Name string } func changeNameByValue(u User) { u.Name = "Vanya" } func changeNameByPointer(u *User) { u.Name = "Petya" } func main() { user := User{Name: "Ivan"} changeNameByValue(user) fmt.Println(user.Name) // Ivan changeNameByPointer(&user) fmt.Println(user.Name) // Petya }
Les pointeurs peuvent-ils pointer vers des constantes ou des littéraux en Go ?
Réponse correcte : Non, en Go, il n'est pas possible de prendre l'adresse d'une constante ou d'un littéral directement. On peut seulement prendre l'adresse d'une variable :
x := 5 p := &x // OK p2 := &10 // Erreur de compilation
Cela est souvent confondu avec des langages où cela est permis.
Histoire
Dans un projet, un développeur a tenté de passer une référence à un élément d'un slice, pensant qu'il pourrait modifier le slice en toute sécurité via un pointeur. Il s'est trompé : le slice lui-même contient un pointeur, mais après un append(), l'adresse du tableau sous-jacent change, et les modifications ne se reflètent pas toujours sur les données d'origine. Cela a conduit à des bugs difficiles à détecter (les données "se perdaient").
Histoire
Dans le projet, une liste de pointeurs vers des variables locales a été créée dans une boucle, et après la sortie de la boucle, tous les pointeurs pointaient vers la même variable (la variable itérée de la boucle). L'erreur n'a été remarquée qu'après un crash en production.
Histoire
Un développeur a à tort pensé qu'assigner un pointeur libérait l'objet précédent de la mémoire, et a explicitement assigné nil au pointeur, s'attendant à un GC immédiat. En pratique, en Go, le ramasse-miettes décide lui-même quand nettoyer les objets, ignorant l'annulation prématurée des références. Cela a conduit à des fuites là où l'on comptait sur une libération de mémoire opportune.