StringBuffer și StringBuilder
Obiectele de tip String sunt imuabile, astfel că toate operațiunile care modifică șirurile de caractere conduc, de fapt, la crearea unui nou șir, ceea ce poate afecta performanța aplicației.
Pentru a soluționa această problemă și pentru a reduce costurile în lucrul cu șiruri, în Java au fost adăugate clasele StringBuffer și StringBuilder. Aceste clase sunt, în esență, șiruri extensibile, care pot fi modificate fără a afecta performanța.
Aceste clase sunt foarte similare, aproape identice, având aceiași constructori și metode, care sunt utilizate în mod identic. Singura diferență dintre ele constă în faptul că StringBuffer este sincronizat și sigur pentru utilizarea în aplicații multi-thread.
Astfel, este mai potrivit pentru aplicațiile multi-thread, în care obiectul poate fi modificat de mai multe fire de execuție. Pe de altă parte, StringBuilder nu este thread-safe, dar funcționează mai rapid în aplicațiile single-thread.
StringBuffer definește patru constructori:
StringBuffer()
StringBuffer(int capacity)
StringBuffer(String str)
StringBuffer(CharSequence chars)
Constructorii similari sunt definiți de StringBuilder:
StringBuilder()
StringBuilder(int capacity)
StringBuilder(String str)
StringBuilder(CharSequence chars)
Să analizăm funcționalitatea acestor clase folosind StringBuffer.
În toate operațiunile cu șiruri, StringBuffer/StringBuilder redistribuie memoria alocată. Pentru a evita prea frecventele redistribuiri de memorie, StringBuffer/StringBuilder rezervă inițial o anumită zonă de memorie care poate fi utilizată ulterior.
Constructorul fără parametri rezervă memorie pentru 16 caractere. Dacă dorim ca numărul de caractere să fie diferit, putem folosi al doilea constructor, care primește numărul de caractere ca parametru.
Constructorii al treilea și al patrulea din ambele clase primesc un șir sau o secvență de caractere și rezervă memorie suplimentară pentru încă 16 caractere.
Cu metoda capacity() putem obține numărul de caractere pentru care este rezervată memoria, iar cu metoda ensureCapacity() putem modifica capacitatea minimă a bufferului de caractere:
String str = "Java";
StringBuffer strBuffer = new StringBuffer(str);
System.out.println("Capacitate: " + strBuffer.capacity()); // 20
strBuffer.ensureCapacity(32);
System.out.println("Capacitate: " + strBuffer.capacity()); // 42
System.out.println("Lungime: " + strBuffer.length()); // 4
Deoarece StringBuffer este inițializat cu șirul "Java", capacitatea sa este de 4 + 16 = 20 de caractere. Apoi, creștem capacitatea bufferului prin apelul la strBuffer.ensureCapacity(32), ridicând capacitatea minimă la 32 de caractere. Cu toate acestea, capacitatea finală poate fi mai mare, cum este cazul aici, unde capacitatea devine 42 de caractere.
Acest lucru se întâmplă deoarece Java alocă memorie suplimentară pentru a îmbunătăți eficiența.
Totuși, indiferent de capacitate, lungimea șirului, care poate fi obținută cu metoda length(), rămâne aceeași - 4 caractere (deoarece "Java" are 4 caractere).
Pentru a obține șirul care este stocat în StringBuffer, putem folosi metoda standard toString():
String str = "Java";
StringBuffer strBuffer = new StringBuffer(str);
System.out.println(strBuffer.toString()); // Java
În toate operațiunile sale, StringBuffer și StringBuilder sunt asemănătoare cu clasa String.
Obținerea și setarea caracterelor
Metoda charAt() obține, iar metoda setCharAt() setează un caracter la un index specific:
StringBuffer strBuffer = new StringBuffer("Java");
char c = strBuffer.charAt(0); // J
System.out.println(c);
strBuffer.setCharAt(0, 'c');
System.out.println(strBuffer.toString()); // cava
Metoda getChars() obține un set de caractere între indexurile specificate:
StringBuffer strBuffer = new StringBuffer("world");
int startIndex = 1;
int endIndex = 4;
char[] buffer = new char[endIndex - startIndex];
strBuffer.getChars(startIndex, endIndex, buffer, 0);
System.out.println(buffer); // orl
Adăugarea în șir
Metoda append() adaugă un subșir la finalul unui StringBuffer:
StringBuffer strBuffer = new StringBuffer("hello");
strBuffer.append(" world");
System.out.println(strBuffer.toString()); // hello world
Metoda insert() adaugă un șir sau un caracter la un anumit index în StringBuffer:
StringBuffer strBuffer = new StringBuffer("word");
strBuffer.insert(3, 'l');
System.out.println(strBuffer.toString()); // world
strBuffer.insert(0, "s");
System.out.println(strBuffer.toString()); // sworld
Ștergerea caracterelor
Metoda delete() șterge toate caracterele de la un anumit index până la o anumită poziție, iar metoda deleteCharAt() șterge un caracter la un anumit index:
StringBuffer strBuffer = new StringBuffer("assembler");
strBuffer.delete(0, 2);
System.out.println(strBuffer.toString()); // sembler
strBuffer.deleteCharAt(6);
System.out.println(strBuffer.toString()); // semble
Decuparea șirului
Metoda substring() taie șirul de la un anumit index până la sfârșit sau până la un anumit index:
StringBuffer strBuffer = new StringBuffer("hello java!");
String str1 = strBuffer.substring(6); // taie de la caracterul 6 până la sfârșit
System.out.println(str1); // java!
String str2 = strBuffer.substring(3, 9); // taie de la caracterul 3 până la 9
System.out.println(str2); // lo jav
Modificarea lungimii
Pentru a modifica lungimea unui StringBuffer (nu capacitatea bufferului), se folosește metoda setLength(). Dacă StringBuffer crește, șirul este completat cu caractere goale la sfârșit, iar dacă scade, șirul este tăiat:
StringBuffer strBuffer = new StringBuffer("hello");
strBuffer.setLength(10);
System.out.println(strBuffer.toString()); //"hello "
strBuffer.setLength(4);
System.out.println(strBuffer.toString()); //"hell"
Înlocuirea în șir
Pentru a înlocui un subșir între anumite poziții în StringBuffer cu alt subșir, se folosește metoda replace():
StringBuffer strBuffer = new StringBuffer("hello world!");
strBuffer.replace(6, 11, "java");
System.out.println(strBuffer.toString()); // hello java!
Primul parametru al metodei replace() indică poziția de început a înlocuirii, al doilea parametru indică poziția de sfârșit, iar al treilea parametru indică subșirul de înlocuire.
Ordinea inversă a șirului
Metoda reverse() inversează ordinea șirului în StringBuffer:
StringBuffer strBuffer = new StringBuffer("assembler");
strBuffer.reverse();
System.out.println(strBuffer.toString()); // relbmessa