PHP Прохождение по ссылке странный результат [дубликат]

Я просто добавляю небольшие детали:

  new FileWriter («outfilename», true)  

2.nd (true) - это функция ( или, интерфейс), называемый appendable ( http://docs.oracle.com/javase/7/docs/api/java/lang/Appendable.html ). Он отвечает за возможность добавления некоторого контента в конец конкретного файла / потока. Этот интерфейс реализован с Java 1.5. Каждый объект (например, BufferedWriter, CharArrayWriter, CharBuffer, FileWriter, FilterWriter, LogStream, OutputStreamWriter, PipedWriter, PrintStream, PrintWriter, StringBuffer, StringBuilder, StringWriter, Writer) с этим интерфейсом может использоваться для добавления контента

В других слова, вы можете добавить некоторый контент в свой gzip-файл или какой-то http-процесс

33
задан neworld 3 February 2012 в 12:40
поделиться

2 ответа

Это хорошо документированное поведение PHP. См. предупреждение на странице foreach php.net

Warning

Ссылка на $ value , а последний элемент массива остается даже после цикла foreach . Рекомендуется уничтожить его unset ().

$a = array('a', 'b', 'c', 'd');

foreach ($a as &$v) { }
unset($v);
foreach ($a as $v) { }

print_r($a);

EDIT

Попытайтесь пошаговое руководство к тому, что на самом деле происходит здесь

$a = array('a', 'b', 'c', 'd');
foreach ($a as &$v) { }   // 1st iteration $v is a reference to $a[0] ('a')
foreach ($a as &$v) { }   // 2nd iteration $v is a reference to $a[1] ('b')
foreach ($a as &$v) { }   // 3rd iteration $v is a reference to $a[2] ('c')
foreach ($a as &$v) { }   // 4th iteration $v is a reference to $a[3] ('d')

                          // At the end of the foreach loop,
                          //    $v is still a reference to $a[3] ('d')

foreach ($a as $v) { }    // 1st iteration $v (still a reference to $a[3]) 
                          //    is set to a value of $a[0] ('a').
                          //    Because it is a reference to $a[3], 
                          //    it sets $a[3] to 'a'.
foreach ($a as $v) { }    // 2nd iteration $v (still a reference to $a[3]) 
                          //    is set to a value of $a[1] ('b').
                          //    Because it is a reference to $a[3], 
                          //    it sets $a[3] to 'b'.
foreach ($a as $v) { }    // 3rd iteration $v (still a reference to $a[3]) 
                          //    is set to a value of $a[2] ('c').
                          //    Because it is a reference to $a[3], 
                          //    it sets $a[3] to 'c'.
foreach ($a as $v) { }    // 4th iteration $v (still a reference to $a[3]) 
                          //    is set to a value of $a[3] ('c' since 
                          //       the last iteration).
                          //    Because it is a reference to $a[3], 
                          //    it sets $a[3] to 'c'.
76
ответ дан Mark Baker 16 August 2018 в 05:27
поделиться
  • 1
    Я знаю это!!! Но что не так в моей программе ??? – Manish Trivedi 11 February 2011 в 14:05
  • 2
    @Manish Trivedi: см. Раздел Warning , почему это происходит. В вашей программе нет ничего плохого. – BoltClock♦ 11 February 2011 в 14:05
  • 3
    Спасибо ..... я получил его – Manish Trivedi 11 February 2011 в 14:07
  • 4
    Очень хорошее объяснение! Спасибо: D Я должен помнить, что в качестве ссылки / обмана, все остальные ответы о ссылках с foreach не объясняют это так хорошо, как вы здесь! – Rizier123 27 March 2015 в 16:45
  • 5
    В вашем unset($v);, почему $v недоступен за пределами foreach? : о – nawfal 20 November 2015 в 14:15

Первый цикл foreach не производит никаких изменений в массиве, как и ожидалось. Тем не менее, это заставляет $v присваивать ссылку на каждый из элементов $a, так что к моменту окончания первого цикла $v является, по сути, ссылкой на $a[2].

Как только начинается второй цикл, $v теперь назначается значение каждого элемента. Однако $v уже ссылается на $a[2];, поэтому любое присвоенное ему значение будет автоматически скопировано в последний элемент массива!

Таким образом, во время первой итерации $a[2] будет становятся нулевыми, затем одно, а затем снова, будучи эффективно скопированы на себя. Чтобы решить эту проблему, вы всегда должны отключать переменные, которые вы используете в своих циклах foreach by-reference, или, еще лучше, избегать использования прежнего вообще.

3
ответ дан Adam 16 August 2018 в 05:27
поделиться
Другие вопросы по тегам:

Похожие вопросы: