Qual è la differenza tra
foreach ($my_array as $my_value) {
}
E:
foreach ($my_array as &$my_value) {
}
?
Posso chiederti di darmi due esempi reali di quando usarne uno e quando usi l'altro?
Qual è la differenza tra
foreach ($my_array as $my_value) {
}
E:
foreach ($my_array as &$my_value) {
}
?
Posso chiederti di darmi due esempi reali di quando usarne uno e quando usi l'altro?
Il primo esempio crea una copia del valore, mentre il secondo utilizza un riferimento al valore originale. Quindi, dopo il primo foreach
, l'array originale è ancora intatto. Dopo il secondo foreach
, la matrice originale avrebbe potuto essere modificata poiché era gestita per riferimento.
Alcune funzioni PHP native funzionano già in questo modo, ad esempio shuffle()
che riorganizza il contenuto dell'array. Si noterà che questa funzione non restituisce un array, è sufficiente chiamare:
$myArray = array('foo', 'bar', 'fizz', 'buzz');
shuffle($myArray);
// $myArray is now shuffled
e funziona la sua magia poiché funziona con l'array per riferimento invece di creare una copia di esso.
Poi ci sono funzioni che non passano nulla con riferimento ma piuttosto si occupano di una copia del valore originale, come ad esempio ucwords()
che restituisce la nuova stringa risultante:
$myString = "hello world";
$myString = ucwords($myString);
// $myString is now capitalized
Vedi Passing by Reference.
se $ my_value è un oggetto, passa inevitabilmente per riferimento. – Epharion
@Epharion: No, PHP passa sempre da val a meno che non venga detto di passare da ref. E gli oggetti non fanno eccezione a questo. Solo con gli oggetti un passaggio di val si comporta in modo molto simile a un passaggio di ref a causa del modo in cui PHP memorizza gli oggetti;) – NikiC
Jonathan's answers lo descrive molto bene. Solo per completezza, qui sono le sue due esempi:
valori solo lettura:
$my_array = range(0,3);
foreach ($my_array as $my_value) {
echo $my_value . PHP_EOL;
}
aggiungendo qualche numero a ciascun elemento (quindi modifica ogni valore):
foreach ($my_array as &$my_value) {
$my_value += 42;
}
Se non si utilizza &$my_value
, l'aggiunta non avrà alcun effetto su $my_array
. Ma si potrebbe scrivere gli stessi che non utilizzano i riferimenti:
foreach($my_array as $key=>$value) {
$my_array[$key] = $value + 42;
}
La differenza è che stiamo accedendo/modifica del valore originale direttamente con $my_array[$key]
.
Grazie mille, i tuoi esempi sono chiari come l'acqua. –
Quando prefisso una variabile con una e commerciale, si sta creando un “riferimento”. Riferimenti PHP sono come scorciatoie o collegamenti simbolici sul computer. È possibile creare una variabile puntatore che è solo un altro nome per gli stessi dati.
Non vedo una grande differenza nell'usarli, tranne che NON COPIARE una memoria a memoria variabile. Quando si passano variabili, è sufficiente passare il riferimento e i punti di riferimento all'oggetto originale.
Un tipico errore da principiante: pensare che PHP sia stupido. PHP non copia ciecamente i valori. Usa il concetto copy-on-write, cioè che il valore viene copiato solo quando viene modificato. La creazione di riferimenti per motivi di prestazioni normalmente è solo controproducente, perché spesso fa in modo che PHP esegua solo più copie. – NikiC
Un vero esempio del mondo per & uso è quando si ha bisogno di modificare il contenuto di un array con poche righe di codice
foreach($arrFeed as &$objFeed)
$objFeed['externalSrc'] = convertToLocalImage($objFeed['externalSrc']);
Come regola generale, non usare mai i riferimenti. – troelskn
@troelskn: questa è una stupida regola empirica. A volte devi usarli. Se non sai se dovresti usarli, probabilmente non devi. Ma ogni volta che vuoi modificare il valore reale devi usare i riferimenti. –
@Felix Kling: concordo con @troelskn. Non ho mai avuto la necessità di modificare il valore reale di un array. Ogni volta che dovevo, puoi fare un codice molto più bello dell'uso ('& $ var'). L'unico modo che posso pensare può essere ... l'ottimizzazione: se usi '&', suppongo (correggimi se sbaglio) che non è necessario fare una copia in una variabile temporanea. Quindi guadagno del tempo di esecuzione. Se hai un esempio in cui non puoi evitare cicli come quello con '&' nella mia domanda, posso chiederti di mostrarli come commento qui? Grazie mille! –