JavaRush /Blog Java /Random-MS /Pengenalan kepada String, StringBuffer dan StringBuilder ...

Pengenalan kepada String, StringBuffer dan StringBuilder dalam Java

Diterbitkan dalam kumpulan
Terdapat tiga kelas dalam Java untuk bekerja dengan data teks: String , StringBuffer dan StringBuilder . Setiap pembangun menemui yang pertama pada awal pembelajaran bahasa. Bagaimana dengan baki dua lagi? Apakah perbezaan mereka, dan bilakah lebih baik menggunakan satu atau kelas lain? Secara umum, perbezaan di antara mereka adalah kecil, tetapi lebih baik untuk memahami segala-galanya dalam amalan :) Pengenalan kepada String, StringBuffer dan StringBuilder dalam Java - 1

Kelas rentetan

Kelas ini mewakili urutan aksara. Semua literal rentetan yang ditakrifkan dalam atur cara, seperti "Ini ialah Rentetan" ialah contoh kelas String. String mempunyai dua ciri asas:
  • ini adalah kelas yang tidak berubah
  • ini kelas akhir
Secara umum, kelas String tidak boleh mempunyai anak ( final) dan kejadian kelas tidak boleh diubah suai selepas penciptaan ( immutable). Ini memberikan kelas String beberapa kelebihan penting:
  1. Disebabkan oleh ketidakbolehubah, kod cincang contoh kelas String dicache. Ia tidak perlu dinilai setiap kali kerana nilai medan objek tidak akan berubah selepas ia dibuat. Ini memberikan prestasi tinggi apabila menggunakan kelas ini sebagai kunci untuk HashMap.

  2. Kelas String boleh digunakan dalam persekitaran berbilang benang tanpa penyegerakan tambahan.

  3. Satu lagi ciri kelas String ialah ia membebankan +operator " " dalam Java. Oleh itu, penggabungan (penambahan) rentetan agak mudah:

public static void main(String[] args) {
    String command = "Follow" + " " + "the" + " " + "white" + " " + "rabbit";
    System.out.println(command); // Follow the white rabbit
}
Di bawah tudung, penggabungan rentetan dilakukan oleh kelas StringBuilder atau StringBuffer (mengikut budi bicara pengkompil) dan kaedah append(kita akan bercakap tentang kelas ini sedikit kemudian). Jika kita menambah contoh kelas String dengan contoh kelas lain, yang terakhir akan dikurangkan kepada perwakilan rentetan:
public static void main(String[] args) {
    Boolean b = Boolean.TRUE;
    String result = "b is " + b;
    System.out.println(result); //b is true
}
Ini adalah satu lagi sifat menarik kelas String: objek dari mana-mana kelas boleh dihantar ke perwakilan rentetan menggunakan kaedah toString()yang ditakrifkan dalam kelas Objectdan diwarisi oleh semua kelas lain. Selalunya kaedah toString() pada objek dipanggil secara tersirat. Contohnya, apabila kita memaparkan sesuatu pada skrin atau menambah String pada objek kelas lain. Kelas String mempunyai satu lagi ciri. Semua literal rentetan yang ditakrifkan dalam kod Java, seperti "asdf", dicache pada masa penyusunan dan ditambahkan pada kumpulan rentetan yang dipanggil. Jika kita menjalankan kod berikut:
String a = "Wake up, Neo";
String b = "Wake up, Neo";

System.out.println(a == b);
Kita akan melihat benar dalam konsol kerana pembolehubah asebenarnya akan bmerujuk kepada contoh kelas String yang sama yang telah ditambahkan pada kolam rentetan pada masa penyusunan. Iaitu, contoh kelas yang berbeza dengan nilai yang sama tidak dibuat, dan memori disimpan.

Kelemahan:

Tidak sukar untuk meneka bahawa kelas String diperlukan terutamanya untuk bekerja dengan rentetan. Tetapi dalam beberapa kes, ciri kelas String di atas boleh bertukar daripada kelebihan kepada keburukan. Sebaik sahaja rentetan dibuat dalam kod Java, banyak operasi sering dilakukan padanya:
  • menukar rentetan kepada daftar yang berbeza;
  • pengekstrakan substring;
  • penyatuan;
  • dan lain-lain.
Mari lihat kod ini:
public static void main(String[] args) {

    String s = " Wake up, Neo! ";
    s = s.toUpperCase();
    s = s.trim();

    System.out.println("\"" + s + "\"");
}
Pada pandangan pertama, nampaknya kami baru sahaja menterjemah baris "Bangun, Neo!" kepada huruf besar, mengalih keluar ruang tambahan daripada rentetan ini dan membungkusnya dengan petikan. Malah, disebabkan oleh ketidakbolehubah kelas String, hasil daripada setiap operasi, contoh rentetan baharu dicipta dan contoh rentetan lama dibuang, menghasilkan sejumlah besar sampah. Bagaimana untuk mengelakkan pembaziran ingatan?

Kelas StringBuffer

Untuk mengendalikan penciptaan sampah sementara akibat pengubahsuaian pada objek String, anda boleh menggunakan kelas StringBuffer. Ini ialah mutablekelas, i.e. boleh ubah. Objek kelas StringBuffer boleh mengandungi set aksara tertentu, panjang dan nilainya boleh diubah dengan memanggil kaedah tertentu. Mari lihat bagaimana kelas ini berfungsi. Untuk mencipta objek baharu, gunakan salah satu daripada pembinanya, sebagai contoh:
  • StringBuffer() - akan mencipta objek kosong (tiada aksara).
  • StringBuffer(String str) - akan mencipta objek berdasarkan pembolehubah str (mengandungi semua aksara str dalam urutan yang sama)
Amalan:
StringBuffer sb = new StringBuffer();
StringBuffer sb2 = new StringBuffer("Not empty");
Penggabungan rentetan melalui StringBuffer di Jawa dilakukan menggunakan append. Secara umum, kaedah appenddalam kelas StringBuffer dibebankan sedemikian rupa sehingga ia boleh menerima hampir semua jenis data:
public static void main(String[] args) {
    StringBuffer sb = new StringBuffer();

    sb.append(new Integer(2));
    sb.append("; ");
    sb.append(false);
    sb.append("; ");
    sb.append(Arrays.asList(1,2,3));
    sb.append("; ");

    System.out.println(sb); // 2; false; [1, 2, 3];
}
Kaedah ini appendmengembalikan objek di mana ia dipanggil (seperti banyak kaedah lain), yang membolehkan ia dipanggil dalam "rantai". Contoh di atas boleh ditulis seperti ini:
public static void main(String[] args) {
    StringBuffer sb = new StringBuffer();

    sb.append(new Integer(2))
            .append("; ")
            .append(false)
            .append("; ")
            .append(Arrays.asList(1,2,3))
            .append("; ");

    System.out.println(sb); // 2; false; [1, 2, 3];
}
Kelas StringBuffer mempunyai beberapa kaedah untuk bekerja dengan rentetan. Mari kita senaraikan yang utama:
  • delete(int start, int end)— memadam subrentetan aksara bermula dari kedudukan start, berakhirend
  • deleteCharAt(int index)— memadam aksara pada kedudukanindex
  • insert(int offset, String str)— memasukkan garisan strpada kedudukan offset. Kaedah ini insertjuga terlebih beban dan boleh mengambil hujah yang berbeza
  • replace(int start, int end, String str)- akan menggantikan semua aksara dari kedudukan startke kedudukan enddenganstr
  • reverse()— membalikkan susunan semua aksara
  • substring(int start)- akan mengembalikan subrentetan bermula pada kedudukan start
  • substring(int start, int end)- akan mengembalikan subrentetan bermula dari kedudukan startke kedudukanend
Senarai lengkap kaedah dan pembina terdapat dalam dokumentasi rasmi . Bagaimanakah kaedah di atas berfungsi? Mari lihat dalam amalan:
public static void main(String[] args) {
     String numbers = "0123456789";

     StringBuffer sb = new StringBuffer(numbers);

     System.out.println(sb.substring(3)); // 3456789
     System.out.println(sb.substring(4, 8)); // 4567
     System.out.println(sb.replace(3, 5, "ABCDE")); // 012ABCDE56789

     sb = new StringBuffer(numbers);
     System.out.println(sb.reverse()); // 9876543210
     sb.reverse(); // Return the original order

     sb = new StringBuffer(numbers);
     System.out.println(sb.delete(5, 9)); // 012349
     System.out.println(sb.deleteCharAt(1)); // 02349
     System.out.println(sb.insert(1, "One")); // 0One2349
    }

Kelebihan:

  1. Seperti yang telah disebutkan, StringBuffer ialah kelas boleh ubah, jadi bekerja dengannya tidak menghasilkan jumlah sampah memori yang sama seperti dengan String. Oleh itu, jika banyak pengubahsuaian dibuat pada rentetan, lebih baik menggunakan StringBuffer.

  2. StringBuffer ialah kelas selamat benang. Kaedahnya disegerakkan dan kejadian boleh digunakan oleh berbilang benang secara serentak.

Kelemahan:

Di satu pihak, keselamatan benang adalah kelebihan kelas, dan sebaliknya, ia adalah kelemahan. Kaedah disegerakkan adalah lebih perlahan daripada kaedah tidak disegerakkan. Di sinilah StringBuilder berperanan. Mari kita fikirkan jenis kelas Java ini - StringBuilder, kaedah apa yang ada dan ciri-cirinya.

Kelas StringBuilder

StringBuilder dalam Java ialah kelas yang mewakili jujukan aksara. Ia sangat serupa dengan StringBuffer dalam semua cara kecuali keselamatan benang. StringBuilder menyediakan API yang serupa dengan StringBuffer. Mari kita tunjukkan ini menggunakan contoh biasa, menggantikan pengisytiharan pembolehubah daripada StringBufer kepada StringBuilder:
public static void main(String[] args) {
    String numbers = "0123456789";

    StringBuilder sb = new StringBuilder(numbers);

    System.out.println(sb.substring(3)); //3456789
    System.out.println(sb.substring(4, 8)); //4567
    System.out.println(sb.replace(3, 5, "ABCDE")); //012ABCDE56789

    sb = new StringBuilder(numbers);
    System.out.println(sb.reverse()); //9876543210
    sb.reverse(); // Return the original order

    sb = new StringBuilder(numbers);
    System.out.println(sb.delete(5, 9)); //012349
    System.out.println(sb.deleteCharAt(1)); //02349
    System.out.println(sb.insert(1, "One")); //0One2349
}
Satu-satunya perbezaan ialah StringBuffer adalah selamat untuk thread dan semua kaedahnya disegerakkan, manakala StringBuilder tidak. Ini adalah satu-satunya ciri. StringBuilder di Java lebih pantas daripada StringBuffer kerana kaedah yang tidak disegerakkan. Oleh itu, dalam kebanyakan kes, kecuali dalam persekitaran berbilang benang, lebih baik menggunakan StringBuilder untuk program Java. Kami meringkaskan segala-galanya dalam jadual perbandingan tiga kelas:

String vs StringBuffer vs StringBuilder

Tali StringBuffer StringBuilder
Kebolehubah Immutable(Tidak) mutable(Ya) mutable(Ya)
Kebolehlanjutan final(Tidak) final(Tidak) final(Tidak)
Keselamatan benang Ya, kerana ketidakbolehubahannya Ya, disebabkan penyegerakan Tidak
Bila nak guna Apabila bekerja dengan rentetan yang jarang diubah suai Apabila bekerja dengan rentetan yang akan diubah suai dengan kerap dalam persekitaran berbilang benang Apabila bekerja dengan rentetan yang akan diubah suai dengan kerap dalam persekitaran berbenang tunggal
Anda boleh mempelajari topik ini dengan lebih terperinci pada tahap kedua pencarian Java Multithreading dalam kursus JavaRush:
Komen
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION