it-swarm-id.com

Rangkaian string dalam Java - kapan harus menggunakan +, StringBuilder dan concat

Kapan kita harus menggunakan + untuk rangkaian string, kapan StringBuilder lebih disukai dan Kapan cocok untuk menggunakan concat.

Saya pernah mendengar StringBuilder lebih disukai untuk penggabungan dalam loop. Kenapa gitu?

Terima kasih.

41
Manish Mulani

Saya cenderung menggunakan StringBuilder pada jalur kode di mana kinerja menjadi perhatian. Penggabungan string berulang dalam satu lingkaran sering kali merupakan kandidat yang baik.

Alasan memilih StringBuilder adalah karena keduanya + dan concat membuat objek baru setiap kali Anda memanggil mereka (asalkan argumen sisi kanan tidak kosong). Ini dapat dengan cepat ditambahkan ke banyak objek, hampir semuanya benar-benar tidak perlu.

Seperti yang ditunjukkan orang lain, saat Anda menggunakan + beberapa kali dalam pernyataan yang sama, kompiler sering dapat mengoptimalkan ini untuk Anda. Namun, dalam pengalaman saya, argumen ini tidak berlaku ketika rangkuman terjadi dalam pernyataan terpisah. Itu tentu tidak membantu dengan loop.

Setelah mengatakan semua ini, saya pikir prioritas utama harus menulis kode yang jelas. Ada beberapa alat profil hebat yang tersedia untuk Java (Saya menggunakan YourKit), yang membuatnya sangat mudah untuk menunjukkan hambatan kinerja dan mengoptimalkan hanya bit yang penting.

P.S. Saya tidak pernah perlu menggunakan concat.

31
NPE

Modern Java kompiler mengonversi operasi + Anda dengan menambahkan StringBuilder. Maksud saya katakan jika Anda melakukannya str = str1 + str2 + str3 maka kompiler akan menghasilkan kode berikut:

StringBuilder sb = new StringBuilder();
str = sb.append(str1).append(str2).append(str3).toString();

Anda dapat mendekompilasi kode menggunakan DJ atau Cavaj untuk mengonfirmasi ini :) Jadi sekarang ini lebih merupakan masalah pilihan daripada manfaat kinerja untuk menggunakan + atau StringBuilder :)

Namun mengingat situasi bahwa kompiler tidak melakukannya untuk Anda (jika Anda menggunakan private Java SDK untuk melakukannya maka mungkin saja terjadi), maka tentu saja StringBuilder adalah cara untuk pergi saat Anda mengakhiri up menghindari banyak objek String yang tidak perlu.

47
Saurabh

Dari Java/J2EE Job Interview Companion :

String

String tidak dapat diubah: Anda tidak dapat mengubah objek String tetapi dapat menggantinya dengan membuat instance baru. Membuat instance baru agak mahal.

//Inefficient version using immutable String
String output = "Some text";
int count = 100;
for (int i = 0; i < count; i++) {
    output += i;
}
return output;

Kode di atas akan membangun 99 objek String baru, yang 98 akan segera dibuang. Membuat objek baru tidak efisien.

StringBuffer/StringBuilder

StringBuffer bisa berubah: gunakan StringBuffer atau StringBuilder ketika Anda ingin mengubah konten. StringBuilder ditambahkan dalam Java 5 dan identik dalam semua hal dengan StringBuffer kecuali bahwa itu tidak disinkronkan, yang membuatnya sedikit lebih cepat dengan biaya tidak aman untuk thread.

//More efficient version using mutable StringBuffer
StringBuffer output = new StringBuffer(110);
output.append("Some text");
for (int i = 0; i < count; i++) {
  output.append(i);
}
return output.toString();

Kode di atas hanya membuat dua objek baru, StringBuffer dan yang terakhir String yang dikembalikan. StringBuffer perluas sesuai kebutuhan, yang biayanya mahal, jadi akan lebih baik untuk menginisialisasi StringBuffer dengan ukuran yang benar dari awal seperti yang ditunjukkan.

15
dim1902

Jika semua elemen gabungan adalah konstanta (contoh: "these" + "are" + "constants"), maka saya lebih suka +, karena kompiler akan menyatukan rangkaian untuk Anda. Kalau tidak, menggunakan StringBuilder adalah cara yang paling efektif.

Jika Anda menggunakan + dengan non-konstanta, Compiler akan secara internal menggunakan StringBuilder juga, tetapi debugging menjadi neraka, karena kode yang digunakan tidak lagi identik dengan kode sumber Anda.

5

Rekomendasi saya adalah sebagai berikut:

  • +: Gunakan saat menggabungkan 2 atau 3 Strings hanya untuk menjaga kode Anda singkat dan mudah dibaca.
  • StringBuilder: Gunakan ketika membangun output String yang kompleks atau di mana kinerja menjadi perhatian.
  • String.format: Anda tidak menyebutkan ini dalam pertanyaan Anda tetapi ini adalah metode pilihan saya untuk membuat Strings karena membuat kode yang paling mudah dibaca/ringkas menurut pendapat saya dan sangat berguna untuk pernyataan log.
  • concat: Saya rasa saya tidak pernah punya alasan untuk menggunakan ini.
2
Adamski

Gunakan StringBuilder jika Anda melakukan banyak manipulasi. Biasanya loop adalah indikasi yang cukup bagus tentang ini.

Alasan untuk ini adalah bahwa menggunakan penggabungan normal menghasilkan banyak objek antara String perantara yang tidak dapat dengan mudah "diperpanjang" (yaitu setiap operasi penggabungan menghasilkan copy, membutuhkan memori dan waktu CPU untuk membuat). A StringBuilder di sisi lain hanya perlu menyalin data dalam beberapa kasus (memasukkan sesuatu di tengah, atau harus mengubah ukuran karena hasilnya menjadi besar), sehingga menghemat operasi penyalinan tersebut.

Menggunakan concat() tidak memiliki manfaat nyata jika menggunakan + (Mungkin sedikit lebih cepat untuk satu +, Tetapi begitu Anda melakukannya a.concat(b).concat(c) it akan benar-benar lebih lambat dari a + b + c).

1
Joachim Sauer

Saya menyarankan untuk menggunakan concat untuk dua string concatenation dan StringBuilder sebaliknya, lihat penjelasan saya untuk operator concatenation (+) vs concat ()

1

Gunakan + untuk pernyataan tunggal dan StringBuilder untuk banyak pernyataan/loop.

1
Puce

Perolehan kinerja dari kompiler berlaku untuk konstanta gabungan . Penggunaan lainnya sebenarnya lebih lambat daripada menggunakan StringBuilder secara langsung.

Tidak ada masalah dengan menggunakan "+" mis. untuk membuat pesan untuk Pengecualian karena itu tidak sering terjadi dan aplikasi sudah entah bagaimana kacau saat ini. Hindari menggunakan "+" dalam loop.

Untuk membuat pesan yang bermakna atau string parametrized lainnya (mis. Ekspresi Xpath), gunakan String.format - itu jauh lebih baik dibaca.

1
Rostislav Matl