Domanda

Le stringhe sono immutabili, nel senso che una volta create non possono essere modificate.

Quindi, ciò significa che ci vorrebbe più memoria se si aggiungessero cose con + = che se si creasse StringBuffer e si aggiungesse del testo a questo?

Se usi + =, creeresti un nuovo "oggetto" ogni volta che deve essere salvato in memoria, vero?

È stato utile?

Soluzione

Sì, creerai un nuovo oggetto ogni volta con + =. Ciò non significa che sia sempre la cosa sbagliata da fare, tuttavia. Dipende se vuoi quel valore come stringa o se lo userai solo per costruire ulteriormente la stringa.

Se in realtà vuoi il risultato di x + y come stringa, allora potresti anche usare la concatenazione di stringhe. Tuttavia, se hai davvero intenzione di (diciamo) fare un giro circolare e aggiungere un'altra stringa, e un'altra, ecc. - Il risultato è solo una stringa alla fine, quindi StringBuffer / StringBuilder sono la strada da percorrere. In effetti, il looping è davvero il punto in cui StringBuilder ripaga della concatenazione di stringhe - la differenza di prestazioni per 5 o anche 10 concatenazioni dirette sarà piuttosto piccola, ma per migliaia diventa molto peggio - fondamentalmente perché ottieni O (N 2 ) complessità con concatenazione vs O (N) complessità con StringBuilder.

In Java 5 e versioni successive, dovresti fondamentalmente usare StringBuilder: non è sincronizzato, ma va quasi sempre bene; è molto raro volerne condividere uno tra i thread.

Ho un su tutto questo che potresti trovare utile.

Altri suggerimenti

La regola empirica è semplice:

Se si eseguono concatenazioni in un ciclo, non utilizzare +=

Se non stai eseguendo concatenazioni in un ciclo, l'uso di + = semplicemente non ha importanza. (A meno che un'applicazione critica per le prestazioni

In Java 5 o versioni successive, StringBuffer è thread-safe, quindi ha un overhead che non si dovrebbe pagare a meno che non sia necessario. StringBuilder ha la stessa API ma non è sicuro per i thread (vale a dire, dovresti usarlo solo all'interno di un singolo thread).

Sì, se si creano stringhe di grandi dimensioni, è più efficiente utilizzare StringBuilder. Probabilmente non ne vale la pena passare StringBuilder o StringBuffer come parte dell'API. Questo è troppo confuso.

Sono d'accordo con tutte le risposte postate sopra, ma ti aiuterà un po 'a capire di più sulla modalità di implementazione di Java. La JVM utilizza StringBuffer internamente per compilare l'operatore String + (From StringBuffer Javadoc ):

  

I buffer di stringa sono utilizzati dal   compilatore per implementare il binario   operatore di concatenazione di stringhe +. Per   esempio, il codice:

     x = "a" + 4 + "c"
     

è compilato all'equivalente di:

     x = new StringBuffer().append("a").append(4).append("c")
                           .toString()

Allo stesso modo, x + = " alcune nuove stringhe " equivalgono a x = x + " alcune nuove stringhe " . Vedi dove sto andando con questo?

Se stai eseguendo molte concatenazioni di stringhe, l'utilizzo di StringBuffer aumenterà le tue prestazioni, ma se stai facendo solo un paio di semplici concatenazioni di stringhe, il compilatore Java probabilmente lo ottimizzerà per te e non noterai una differenza nelle prestazioni

Sì. La stringa è immutabile. Per un uso occasionale, + = è OK. Se l'operazione + = è intensiva, è necessario passare a StringBuilder.

Ma il Garbage Collector finirà per liberare le vecchie stringhe una volta che non ci sono riferimenti ad esse

Esattamente. Dovresti usare StringBuilder anche se la sicurezza dei thread non è un problema.

Come nota a margine: potrebbero esserci diversi oggetti String che utilizzano lo stesso carattere di supporto [] - ad esempio ogni volta che si utilizza la sottostringa (), non verrà creato alcun nuovo carattere [] che lo renda abbastanza efficiente.

Inoltre, i compilatori potrebbero fare alcune ottimizzazioni per te. Ad esempio, se lo fai

static final String FOO = "foo";
static final String BAR = "bar"; 

String getFoobar() {
  return FOO + BAR; // no string concatenation at runtime
}

Non sarei sorpreso se il compilatore usasse StringBuilder internamente per ottimizzare la concatenazione di stringhe ove possibile - se non già forse in futuro.

Penso che si basi sul GC per raccogliere la memoria con la stringa abbandonata. Quindi fare + = con string builder sarà decisamente più veloce se hai molte operazioni sulla manipolazione delle stringhe. Ma non dovrebbe essere un problema per la maggior parte dei casi.

Sì, e questo è esattamente il motivo per cui dovresti usare StringBuffer per concatenare molte stringhe.

Nota anche che da Java 5 dovresti anche preferire StringBuilder per la maggior parte del tempo. È solo una sorta di StringBuffer non sincronizzato.

Hai ragione sul fatto che le stringhe sono immutabili, quindi se stai cercando di conservare la memoria mentre fai molta concatenazione di stringhe, dovresti usare StringBuilder anziché + =.

Tuttavia, potresti non preoccuparti. I programmi sono scritti per i loro lettori umani, quindi puoi andare con chiarezza. Se è importante ottimizzare, è necessario prima profilare. A meno che il programma non sia pesantemente ponderato per l'attività delle stringhe, probabilmente ci saranno altri colli di bottiglia.

No

Non utilizzerà più memoria. Sì, vengono creati nuovi oggetti, ma quelli vecchi vengono riciclati. Alla fine, la quantità di memoria utilizzata è la stessa.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top