Heim >Backend-Entwicklung >Golang >Warum liefert die „Range'-Schleife von Go bei unterschiedlichen Schleifenstrukturen unterschiedliche Ergebnisse?

Warum liefert die „Range'-Schleife von Go bei unterschiedlichen Schleifenstrukturen unterschiedliche Ergebnisse?

Patricia Arquette
Patricia ArquetteOriginal
2024-12-19 18:20:101025Durchsuche

Why Does Go's `range` Loop Produce Different Results with Varying Loop Structures?

Verstehen der verschiedenen Schleifenvariationen in Go

Beim Durchlaufen eines Slice in Go kann es bei Verwendung der Bereichsmethode zu unerwartetem Verhalten kommen. Lassen Sie uns untersuchen, warum verschiedene Schleifenvarianten zu unterschiedlichen Ergebnissen führen können.

Das Problem

Betrachten Sie die folgenden zwei for-Schleifenvarianten:

loop1() {
    for _, cmd := range cmds {
        // Store a function literal that references the loop variable cmd
        actions[cmd] = func() {
            fmt.Println(cmd)
        }
    }
}
loop2() {
    for i, cmd := range cmds {
        // Capture the loop variable cmd using a new variable
        command := cmds[i]
        actions[cmd] = func() {
            fmt.Println(command)
        }
    }
}

Das Ausführen dieser Schleifen führt zu Ergebnissen in verschiedenen Ausgaben:

  • loop1(): Druckt Dreimal „update“
  • loop2(): Gibt „delete“, „update“ und „create“ aus

Die Erklärung

Das Problem mit loop1() entsteht, weil die in der Aktionszuordnung gespeicherten Funktionsliterale auf die Schleifenvariable cmd verweisen. Da es nur eine Instanz dieser Schleifenvariablen gibt, verweisen alle in der Karte gespeicherten Funktionen auf sie.

Wenn die Schleife abgeschlossen ist, ist der Wert von cmd das letzte Element im cmds-Slice „update“. " Wenn die Funktionen in der Aktionszuordnung ausgeführt werden, geben sie daher alle „Update“ aus.

Um dieses Problem zu umgehen, erfasst loop2() die Schleifenvariable cmd mithilfe einer neuen Variablen, dem Befehl. Dadurch wird für jede Iteration eine „getrennte“ Kopie der Schleifenvariablen erstellt, die nach Abschluss der Schleife nicht von der Schleifenvariablen beeinflusst wird.

Als Konsequenz hat jede Funktion, die in der Aktionszuordnung in loop2() gespeichert ist eine eigene Kopie der Schleifenvariablen, die es jeder Funktion ermöglicht, den richtigen Befehl auszugeben.

Fazit

Beim Bereich über einen Slice ist es wichtig, sich darüber im Klaren zu sein, dass die Schleifenvariable wird von allen Iterationen gemeinsam genutzt. Um unerwartetes Verhalten zu vermeiden, empfiehlt es sich, die Schleifenvariable mithilfe einer neuen Variablen zu erfassen oder zu trennen, insbesondere wenn Funktionsliterale verwendet werden, die nach der Schleife ausgeführt werden.

Das obige ist der detaillierte Inhalt vonWarum liefert die „Range'-Schleife von Go bei unterschiedlichen Schleifenstrukturen unterschiedliche Ergebnisse?. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Stellungnahme:
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