php Problem mit Schleifen über ein Array zweimal mit foreach und übergeben Wert als Referenz

8

Ich muss ein Array zweimal durchlaufen - einmal, um seine Werte zu ändern, und einmal, um den Inhalt in HTML anzuzeigen. Leider gerate ich in Schwierigkeiten. Ich habe ein Testszenario erstellt, um das Problem zu veranschaulichen.

%Vor%

Dies gibt aus:

%Vor%

Beachten Sie, dass die Werte für das letzte Element falsch sind.

Wenn ich während der zweiten Iteration verwende foreach($cases as $k => $d) anstelle von foreach($cases as $k => $v) oder wenn ich $v vor der zweiten Iteration (unset($v)) aufschalte, ist alles in Ordnung. Das ist faszinierend. Was vermisse ich?

    
longwing 07.09.2013, 03:48
quelle

4 Antworten

15

Wenn Sie eine foreach -Schleife ausführen, bleiben die Variablen in () bestehen, nachdem die Schleife beendet wurde. Das bedeutet, dass Sie nach Abschluss der ersten Schleife var_dump($v) eingeben und die Werte abrufen können, die nach der letzten Iteration durch die erste Schleife enthalten waren. Dies ist der Fall, egal ob es sich um eine Referenz ( &$v ) oder eine normale Variable ( $v ) handelt.

Wenn es sich jedoch um eine Referenz in der ersten Schleife handelt, bleibt sie eine Referenz, es sei denn, sie ist nicht gesetzt. Das heißt, wenn Sie die zweite Schleife eingeben, überschreiben Sie die Referenz mit dem Wert des Array-Elements, das Sie gerade betrachten.

Denken Sie daran, was foreach($cases as $k => $v) wirklich bedeutet: "Nimm den Schlüssel für dieses Element in $ cases und weise es $ k zu, nimm den Wert für dieses Element und weise es $ v zu"). Da $ v immer noch eine Referenz auf das letzte Element im Array ist, anstatt den Wert einer neuen Variablen $ v zu setzen, aktualisieren Sie den Wert, auf den bereits $ v verweist.

Das heißt, wenn wir $ cases einfach nach dem ersten Mal bis zum zweiten foreach vereinfachen, ist $ cases jetzt ['a', 'b', 'c', 'd'] , weil Sie das Element in $ cases, die $ v points haben, neu zugewiesen haben zu - dem letzten - um den gleichen Wert wie der erste zu haben. Beim zweiten Mal ist es ['a', 'b', 'c', 'a'] . Das dritte Mal durch es ist ['a', 'b', 'c', 'b'] . Dann, das letzte Mal bis Sie es sich selbst zuweisen, und zu diesem Zeitpunkt hält es den Wert ['a', 'b', 'c', 'c'] .

Das ist wirklich nur ein Fall von php funktioniert wie erwartet. Die Lösung ist 'c' , sobald die erste Schleife abgeschlossen ist, um sicherzustellen, dass Sie bei der nächsten Verwendung von $ v eine neue Variable anstelle einer vorhandenen Referenz verwenden.

Um dies in Aktion zu sehen:

Gehe weiter zu Ссылка und füge den folgenden Code ein und führe ihn aus; In der Ausgabe sehen Sie, dass unset($v) nach Abschluss der ersten Schleife beibehalten wird und dass sich der Wert von $v jedes Mal durch die zweite Schleife ändert.

%Vor%     
DiMono 07.09.2013 04:34
quelle
2

Versuchen Sie Folgendes:

%Vor%     
undone 07.09.2013 04:06
quelle
2

Hier ist eine ähnliche Frage, die ein paar gute Erklärungen dafür gibt, warum dieses Problem auftritt.

PHP Pass durch Referenz in foreach

    
NeverForgetY2K 07.09.2013 04:19
quelle
0

Lassen Sie mich wissen, ist dies Ihre Lösung:

%Vor%     
01e 07.09.2013 04:15
quelle