Mục lục
Nếu bạn đã từng code C/C++ thì chắc rằng bạn bạn qua tâm đến việc cấp phát và giải phóng vùng nhớ, công việc này khá vất vả vì nếu không cẩn thận thì chương trình sẽ bị lỗi bất cứ lúc nào vì tràn bộ nhớ.
Bạn thân mình trước đây học 2 năm đầu đại học cũng code C/C++ và rất nhiều lần ứng dụng mình viết bị crash vì tràn bộ nhớ. Thật ra do mình code hơi ngu, chứ máy bạn code C/C++ tốt trông thật cool ngầu.
Trình dọn rác – Garbage Collection trong java
Cuộc đời của mình như sang một trang mới khi bắt đầu học ngôn ngữ java, không còn chương trình crash vì tràn bộ nhớ nữa, cũng không cần phải cẩn chú ý đến việc giải phóng vùng nhớ khi không còn sử dụng thay vào đó java sẽ cung cấp một cơ chế tự động giải phóng các dữ liệu rác khi không còn sử dụng nó có tên gọi là Grabage collection(GC).
Grabage collection sẽ tìm kiếm và xoá các bộ nhớ rác, để làm việc điều đó GC sẽ theo dõi từng object chứa trong JVM Heap và xoá chúng khi không còn sử dụng.
GC hoạt động theo hai bước đơn giản sau:
- Mark: GC sẽ xoá định xem phần nào trong bộ nhớ đang được sử dụng và phần nào không đựợc sử dụng sẽ bị đánh dấu (mark).
- Sweep: GC sẽ xoá các object được đánh dấu ở bước Mark.
Ưu điểm
- Chúng ta không cần cấp phát và giải phóng bộ nhớ một cách thủ công.
- Quản lý memory tự động.
Nhược điểm:
- Vì JVM phải theo dõi các object reference khi chúng khởi tạo và lúc nào cần xoá đi nên sẽ hao tốn nhiều CPU hơn.
- Chúng ta sẽ không được phép kiểm soát và xoá các object không cần thiết.
- Việc quản lý bộ nhớ tự động sẽ không hiệu quả như cách thủ công.
Các triển khai của Grabage collection
JVM có bốn kiểu GC chính
- Serial Grabage Collector
- Parallel Grabage Collector
- CMS Grabage Collector
- G1 Grabage Collector
Serial Grabage Collector
Serial Grabage collector là một dạng triển khai đơn giản của GC, nó hoạt động trên single thread. Vì thế nó không tốt để sử dụng với ứng dụng đa luồng.
Khi Serial GC hoạt động chúng sẽ đóng băng tất các các thead của ứng dụng để thực hiện việc dọn dẹp dữ liệu rác.
Serial GC được sử dụng nhiều trong các ứng dụng không có yêu cầu độ trễ nhỏ và thường chạy trên các máy khách.
Parallel Grabage Collector
Parallel GC là trình dọn rác mặc định của JVM, không giống như Serial GC, Parallel GC được sử dụng trong nhiều thread để quản lý bộ nhớ. Nhưung Parallel GC cũng sẽ đóng băng tất cả các thread khi chúng thực hiện dọc rác.
CMS Grabage Collector
CMS là viết tắt của Concurrent Marm Sweep triển khai nhiều GC để thu gon rác. CMS GC được thiết kế cho ứng dụng yêu cầu độ trễ ngắn và có đủ tài nguyên chia sẽ cho chúng trong khi ứng dụng vẫn đang chạy.
G1 Grabage Collector
G1 GC được thiết kế cho ứng dụng chạy trên các máy tính nhiều bộ xử lý với lượng bộ nhớ lớn.
G1 được cho là sẽ thay thế CMS vì nó cho hiệu suất cao hơn.
G1 sẽ phân vùng heap thành một tập các vùng có kích thước bằng nhau. Khi nó bắt đầu thu gon dữ liệu rác G1 sẽ đánh dấu các object không còn được sử dụng.
Sau khi quá trình đánh dấu hoàn tất, G1 sẽ tìm các phân vùng có ít dữ liệu rác nhất và tiến hành dọn dẹp nó rồi đến phân cùng ít rác kế tiếp cho đến khi hoàn tất đó là lý do tại sao nó có tên gọi là G1 (Grabage First).
Ví dụ minh hoạ cách hoạt động của GC
class Student{ int a; int b; public Student(int a,int b){ this.a = a; this.b = b; } public static void main(String args[]){ Student s1 = new Student(1, 2); Student s2 = new Student(4, 5); Student s3; s3=s2; s2=null; s3=null; } }
B1. Khi chúng ta khởi tạo 2 object s1 và s2 thì chúng ta sẽ có 2 object s1, s1 được lưu vào Heap và s1, s2 là 2 biến reference đến chúng.
Student s1 = new Student(1,2 ); Student s2 = new Student(4, 5);
B2. Khi bạn khai báo s3 và gán nó bằng s2 thì s2 và s3 đều tham chiếu cùng một object.
Student s3; s3=s2;
B3. Khi chúng ta gán s2 và s3 = null thì object s2(a = 4, b = 5) không còn biến nào tham chiếu đến nó. Lúc này nó sẽ được GC đánh dấu và được xoá khởi vùng nhớ Heap sau đó.
Nguồn tham khảo