Il motivo principale per copiare una stringa è "tagliare il bagaglio", cioè per tagliare il sottostante matrice char solo quanto necessario.
Il char array sottostante può essere principalmente troppo grande perché quando si crea una stringa chiamando substring
, il char array può essere condiviso tra la nuova istanza della stringa e l'istanza della stringa di origine; un offset punta al primo carattere e la lunghezza è inclusa.
L'espressione che uso, "tagliare il bagaglio", è presa dal codice sorgente di stringa costruttore di copia:
164 public String(String original) {
165 int size = original.count;
166 char[] originalValue = original.value;
167 char[] v;
168 if (originalValue.length > size) {
169 // The array representing the String is bigger than the new
170 // String itself. Perhaps this constructor is being called
171 // in order to trim the baggage, so make a copy of the array.
172 int off = original.offset;
173 v = Arrays.copyOfRange(originalValue, off, off+size);
174 } else {
175 // The array representing the String is the same
176 // size as the String, so no point in making a copy.
177 v = originalValue;
178 }
179 this.offset = 0;
180 this.count = size;
181 this.value = v;
Questo è qualcosa che molti sviluppatori dimenticano ed è importante perché una piccola stringa può prevenire il garbaging di un array di caratteri più grande. Vedi questa domanda correlata in cui ho già sottolineato questo: Java not garbage collecting memory. Molti sviluppatori considerano che la decisione dei progettisti Java di utilizzare questo vecchio trucco di ottimizzazione che era familiare ai programmatori C, in effetti, faceva più male che bene. Molti di noi lo sanno perché siamo stati morsi e abbiamo dovuto esaminare il codice sorgente di Sun per capire cosa è successo ...
Come sottolinea Marko (vedere i commenti sotto), in OpenJDK, a partire da java 7 Update 6 , substring
non condivide più il char array e il costruttore String(String)
è, quindi, inutile. Ma è ancora veloce (anzi è più veloce di fatto) e poiché questa modifica non è stata propagata a tutte le VM (e probabilmente non a tutti i tuoi clienti) ti consiglio di mantenere questa best practice per usare new String(substring)
quando il vecchio comportamento lo giustificava .
fonte
2012-12-10 15:05:04
Questo non è "troppo localizzato", è una buona domanda applicabile a coloro che lo trovano più tardi, con una risposta molto utile e informativa. –
Vedere [questo] (http://stackoverflow.com/a/465682/1037210) risposta. – Lion
Si noti che le risposte alla domanda simile citata possono probabilmente essere considerate parzialmente obsolete. –