Pada 19 Agustus, Oracle merilis JDK 8u20. JDK 8u20 menyertakan banyak fitur baru, seperti pembaruan compiler Java, dukungan untuk memodifikasi parameter MinHeapFreeRatio dan MaxHeapFreeRatio melalui API saat runtime, dan dokumen panduan penyetelan GC baru. Namun di antara sekian banyak fitur baru, yang paling dinantikan adalah Deduplikasi String. Cara mengurangi penggunaan memori selalu menjadi topik abadi. Dalam aplikasi Java, sering terlihat bahwa objek String menghabiskan 30% memori aplikasi. Fitur deduplikasi string baru dapat membantu mengurangi jejak memori objek String dalam aplikasi. Saat ini, fitur ini hanya tersedia untuk pengumpul sampah G1 dan tidak diaktifkan secara default.
Fabian Lange menjelaskan bagaimana deduplikasi string diimplementasikan:
Copy kode kodenya sebagai berikut:
Pengumpul sampah akan menandai array karakter dari objek String ketika diakses, dan menyimpan nilai hash dari String dan referensi lemah ke dalam array. Ketika pengumpul sampah menemukan objek String lain dengan nilai hash yang sama, ia akan membandingkan kedua objek tersebut karakter demi karakter. Jika keduanya sama persis, satu String akan dimodifikasi agar menunjuk ke array karakter dari String lainnya. Karena array karakter pertama tidak lagi direferensikan, array tersebut dapat didaur ulang. Pengumpul sampah akan mencoba mengurangi biaya seluruh operasi. Misalnya, jika objek String dipindai dan tidak ada duplikat yang ditemukan, maka objek tersebut tidak akan diperiksa lagi dalam periode waktu berikutnya.
Selanjutnya, Fabian Lange menjelaskan efek ajaib dari deduplikasi string melalui kode. Pertama jalankan kode berikut menggunakan Java 8 Update 20 dengan parameter -Xmx256m -XX:+UseG1GC:
Copy kode kodenya sebagai berikut:
kelas publik LotOfStrings {
LinkedList akhir statis pribadi<String> LOTS_OF_STRINGS = LinkedList baru<>();
public static void main(String[] args) melempar Pengecualian {
int iterasi = 0;
sementara (benar) {
untuk (int saya = 0; saya < 100; saya++) {
untuk (int j = 0; j < 1000; j++) {
LOTS_OF_STRINGS.tambahkan(String baru("String " + j));
}
}
iterasi++;
System.out.println("Iterasi yang Bertahan: " + iterasi);
Thread.tidur(100);
}
}
}
Kode akan berakhir berjalan karena pengecualian OutOfMemoryError setelah 30 loop. Setelah menggunakan parameter -XX:+UseStringDeduplication -XX:+PrintStringDeduplicationStatistics untuk mengaktifkan fitur deduplikasi string, program dapat berjalan untuk jangka waktu yang lebih lama. Anda juga dapat mempelajari lebih lanjut tentang detail seluruh proses deduplikasi melalui log JVM. Pembaca diminta untuk mengujinya sendiri.
Terakhir, Fabian Lange juga menjelaskan perbedaan antara deduplikasi string dan residensi string. Keduanya sangat mirip, hanya saja residensi string menggunakan kembali seluruh instance String, sedangkan deduplikasi string hanya menargetkan array karakter dari String.
(Teks lengkap berakhir)