Keluar dari memori: Dalam istilah awam, itu berarti tidak ada cukup memori. Misalnya, terus -menerus membuat objek besar dalam loop tak terbatas akan segera menyebabkan overflow memori.
Kebocoran memori: Mengacu pada pelepasan memori yang tepat waktu setelah mengalokasikan memori ke objek ketika objek tidak lagi digunakan, menghasilkan unit memori yang ditempati dan memori yang tersedia aktual berkurang, seperti kebocoran memori.
Kebocoran memori yang disebabkan oleh metode substring
Substring (int beginindex, int endndex) adalah metode kelas string, tetapi metode ini diimplementasikan sepenuhnya berbeda dalam JDK6 dan JDK7 (meskipun keduanya mencapai efek yang sama). Memahami detail implementasinya dapat membantu Anda menggunakannya dengan lebih baik, karena penggunaan substring yang tidak tepat di JDK1.6 dapat menyebabkan masalah kebocoran memori yang serius.
1. Peran Substring
Metode substring (int beginindex, int endIndex) mengembalikan substring, mulai dari awal string induk dan berakhir di EndIndex-1. Subskrip string induk dimulai pada 0, dan substring berisi beginindex dan bukan endindex
String x = "abcdef"; x = str.substring (1,3); System.out.println (x);
Output dari program di atas adalah "BC"
2. Prinsip Implementasi
Kelas string tidak dapat diubah. Ketika X dipindahkan dalam kalimat kedua di atas, itu akan menunjuk ke objek string baru. Namun, tidak ada deskripsi yang akurat atau mewakili situasi aktual yang terjadi di tumpukan. Apa yang sebenarnya terjadi ketika substring dipanggil adalah perbedaan antara keduanya.
Implementasi Substring di JDK6
Objek string disimpan sebagai array char. Ada 3 bidang di kelas string: nilai char [], int offset, dan int int, yang masing -masing digunakan untuk menyimpan array karakter nyata, posisi awal array, dan jumlah karakter string. 3 variabel ini dapat menentukan string. Ketika metode substring dipanggil, itu akan membuat string baru, tetapi nilai array char di atas masih akan menggunakan nilai array induk asli. Satu -satunya perbedaan antara array orang tua dan anak adalah bahwa nilai -nilai jumlah dan offset berbeda.
Lihatlah kode sumber implementasi substring di JDK6:
Public String Substring (int beginIndex, int endIndex) {if (beginIndex <0) {throw New StringIndexOutOfBoundSException (beginIndex); } if (endIndex> count) {lempar stringIndExoutOfBoundsException baru (endIndex); } if (beginIndex> endIndex) {throw stringIndexOutOfBoundsException baru (EndIndex - beginIndex); } return ((beginIndex == 0) && (endIndex == count))? Ini: string baru (offset + beginIndex, endIndex - beginIndex, value); // Digunakan untuk menggunakan nilai array char yang sama dengan string induk} String (int offset, int count, nilai char []) {this.value = nilai; this.offset = offset; this.count = count; }String str = "abcdefghijklmnopqrst"; string sub = str.substring (1, 3); str = null;
Program sederhana ini memiliki dua variabel string str dan sub. Sub string diperoleh oleh string induk str. Jika program di atas dijalankan di JDK1.6, kita tahu bahwa alokasi ruang memori dari array dilakukan pada tumpukan, maka nilai array char internal sub dan STR adalah sama, yaitu, array char di atas terdiri dari karakter a ~ karakter t. Satu -satunya perbedaan antara STR dan Sub adalah perbedaan antara begininindex dan jumlah panjang karakter dalam array. Dalam kalimat ketiga, kami membuat referensi STR kosong, yang dimaksudkan untuk membebaskan ruang yang ditempati oleh STR, tetapi pada saat ini, GC tidak dapat mendaur ulang array char besar ini karena masih dirujuk di dalam sub string, meskipun sub hanya mencegat sebagian kecil dari susunan besar ini. Ketika STR adalah string yang sangat besar, limbah ini sangat jelas dan bahkan dapat menyebabkan masalah kinerja. Anda dapat menyelesaikan masalah ini dengan:
Ini menggunakan teknologi splicing string, yang akan membuat string baru. String baru ini akan menggunakan array char internal baru untuk menyimpan karakter yang sebenarnya dibutuhkan, sehingga array char dari array induk tidak akan direferensikan oleh sumber lain. Biarkan str = null, dan seluruh ruang yang ditempati oleh STR akan didaur ulang di waktu berikutnya GC didaur ulang. Tapi menulis seperti ini jelas tidak tampan, jadi di JDK7, substring diajukan kembali.
Implementasi Substring di JDK7
Peningkatan implementasi substring di JDK7, yang sebenarnya membuat array char baru di tumpukan untuk substring yang dicegat untuk memegang karakter untuk substring.
Periksa kode sumber implementasi dari metode substring dari kelas string di JDK7:
Public String Substring (int beginIndex, int endIndex) {if (beginIndex <0) {throw New StringIndexOutOfBoundSException (beginIndex); } if (endIndex> value.length) {throw stringIndexOutOfBoundsException baru (endIndex); } int sublen = endIndex - beginIndex; if (sublen <0) {lempar stringIndExoutOfBoundsException baru (sublen); } return ((beginIndex == 0) && (endIndex == value.length))? Ini: string baru (nilai, beginindex, sublen); } string publik (nilai char [], int offset, int count) {if (offset <0) {throw new stringIndExoutOfBoundsException (offset); } if (count <0) {lempar stringIndExoutOfBoundsException baru (count); } // Catatan: Offset atau Count mungkin dekat -1 >>> 1. if (offset> value.length - count) {throw New StringIndExoutOfBoundSException (offset + count); } this.value = arrays.copyofrange (value, offset, offset+count); }Metode CopyOfRange dari kelas array:
public static char [] copyOfrange (char [] asli, int from, int to) {int newlength = to - from; if (newLength <0) melempar IllegalArgumentException baru (dari + ">" + to); char [] copy = new char [newLength]; // Ini untuk membuat sistem array char baru.arraycopy (asli, dari, salin, 0, math.min (original.length - from, newLength)); kembalikan salinan; }Dapat ditemukan bahwa array char baru dibuat untuk substring untuk menyimpan karakter dalam substring. Dengan cara ini, tidak ada hubungan yang diperlukan antara string anak dan string induk. Ketika referensi string induk tidak valid, GC akan mendaur ulang ruang memori yang ditempati oleh string induk.
Meringkaskan
Di atas adalah penjelasan lengkap dari kebocoran memori yang disebabkan oleh metode substring di Java. Saya harap ini akan membantu semua orang. Teman yang tertarik dapat terus merujuk ke topik terkait lainnya di situs ini. Jika ada kekurangan, silakan tinggalkan pesan untuk menunjukkannya. Terima kasih teman atas dukungan Anda untuk situs ini!