Y a-t-il foreach en Go ? Tutoriel pas à pas avec exemples
\n\nSi vous venez en Go depuis Python, JavaScript ou PHP, vous êtes probablement habitué au foreach concis pour parcourir les collections. Et voilà que vous écrivez votre première boucle en Go et vous vous demandez : « Mais où est mon foreach bien-aimé ? N'existe-t-il vraiment pas en Go ? »
Indice : le mot-clé direct foreach n'existe effectivement pas en Go. Mais il y a quelque chose de bien plus flexible et puissant — la construction for range. Dans ce tutoriel, nous allons voir comment fonctionne l'itération en Go, montrer des exemples de code réels et comparer avec le foreach familier d'autres langages.
Pourquoi n'y a-t-il pas de foreach en Go et pourquoi range est-il nécessaire ?
\n\nGo est un langage minimaliste. Ses créateurs ont délibérément évité la duplication des constructions syntaxiques. Au lieu d'ajouter un mot-clé séparé foreach, ils ont étendu les capacités de la boucle for existante. C'est ainsi qu'est né for range — un outil universel pour parcourir les tableaux, les slices, les maps, les chaînes de caractères et même les channels.
Si vous cherchez un équivalent exact de foreach en Go, le voici — for range.
Syntaxe de for range : explication simple
\n\nLa structure de base ressemble à ceci :
\n\nfor index, value := range collection {\n // corps de la boucle\n}\n\nOù :
\n- \n
index— l'indice de l'élément (pour les tableaux et slices) ou la clé (pour les maps). \n value— une copie de la valeur de l'élément. \n collection— votre collection (slice, tableau, map, chaîne ou channel). \n
Point important : value est toujours une copie de l'élément. Si vous modifiez value à l'intérieur de la boucle, l'élément d'origine ne changera pas. Pour modifier les originaux, il faut utiliser l'indice.
Exemple 1 : Parcours d'un slice — équivalent de foreach en Go
\n\nCommençons par le cas le plus courant — le parcours des éléments d'un slice :
\n\npackage main\n\nimport "fmt"\n\nfunc main() {\n fruits := []string{"pomme", "banane", "cerise", "melon"}\n\n fmt.Println("Parcours d'un slice (équivalent foreach) :")\n for index, fruit := range fruits {\n fmt.Printf("Indice %d : %s\\n", index, fruit)\n }\n}\n\nSortie :
\nParcours d'un slice (équivalent foreach) :\nIndice 0 : pomme\nIndice 1 : banane\nIndice 2 : cerise\nIndice 3 : melon\n\nSi vous avez besoin uniquement de l'indice (par exemple, pour modifier des éléments), vous pouvez omettre la valeur :
\n\nfor i := range fruits {\n fruits[i] = "fruit : " + fruits[i]\n}\n\nEt si vous avez besoin uniquement des valeurs — utilisez le tiret bas _ :
for _, fruit := range fruits {\n fmt.Println(fruit)\n}\n\nExemple 2 : Parcours d'une map — foreach classique
\n\nEn Go, il n'y a pas de manière plus élégante de parcourir les maps qu'avec for range :
package main\n\nimport "fmt"\n\nfunc main() {\n ages := map[string]int{\n "Anna": 25,\n "Boris": 30,\n "Victor": 35,\n }\n\n fmt.Println("Parcours d'une map (foreach) :")\n for name, age := range ages {\n fmt.Printf("%s : %d ans\\n", name, age)\n }\n}\n\nL'ordre de parcours d'une map en Go n'est pas garanti. Si vous avez besoin d'un ordre stable, rassemblez les clés dans un slice et triez-le.
\n\nExemple 3 : Parcours d'une chaîne — itération caractère par caractère
\n\nContrairement à de nombreux langages, for range en Go itère sur les runes (caractères Unicode), et non sur les octets :
package main\n\nimport "fmt"\n\nfunc main() {\n text := "Bonjour, Go !"\n\n fmt.Println("Parcours d'une chaîne caractère par caractère :")\n for i, r := range text {\n fmt.Printf("Position %d : caractère '%c' (code %U)\\n", i, r, r)\n }\n}\n\nNotez que l'indice i indique l'octet de début de la rune, et non le numéro d'ordre du caractère. Pour les chaînes avec des caractères