Tôi đã xem xét một số hành vi tò mò liên quan đến thu gom rác trong .Net.Tiêu chí để kích hoạt thu gom rác trong .Net
Chương trình sau sẽ ném OutOfMemoryException rất nhanh (sau ít hơn một giây trên máy 32 bit, 2GB). Trình hoàn thiện Foo không bao giờ được gọi.
class Foo
{
Guid guid = Guid.NewGuid();
byte[] buffer = new byte[1000000];
static Random rand = new Random();
public Foo()
{
// Uncomment the following line and the program will run forever.
// rand.NextBytes(buffer);
}
~Foo()
{
// This finalizer is never called unless the rand.NextBytes
// line in the constructor is uncommented.
}
static public void Main(string args[])
{
for (; ;)
{
new Foo();
}
}
}
Nếu dòng rand.nextBytes không được chú ý, nó sẽ chạy quảng cáo vô hạn và trình kết thúc Foo thường được gọi. Tại sao vậy?
Đoán tốt nhất của tôi là trong trường hợp trước đó, CLR hoặc Windows VMM là lười về phân bổ bộ nhớ vật lý. Bộ đệm không bao giờ được ghi vào, do đó bộ nhớ vật lý không bao giờ được sử dụng. Khi không gian địa chỉ hết, hệ thống bị treo. Trong trường hợp thứ hai, hệ thống hết bộ nhớ vật lý trước khi nó hết dung lượng địa chỉ, GC được kích hoạt và các đối tượng được thu thập.
Tuy nhiên, đây là phần tôi không nhận được. Giả sử lý thuyết của tôi là chính xác, tại sao GC không kích hoạt khi không gian địa chỉ chạy thấp? Nếu lý thuyết của tôi là không chính xác, thì giải thích thực sự là gì?
I 'không chắc chắn bạn có câu trả lời đúng, nhưng bạn đưa tôi vào một ca khúc thú vị. Tôi tắt hai máy tính ảo mà tôi đang chạy (cả với 512MB) và tôi nhận được hành vi của bạn. Khi tôi nạp các VPCs trở lại, tôi đã nhận được hành vi lỗi ban đầu. –
Ngoài ra còn có một số chức năng thú vị trong lớp 'GC' để kiểm tra, nhưng một lần nữa, trong mã thực sự không bao giờ được sử dụng. –
Với VPC đang chạy và Thread.Sleep (0) tại chỗ, chương trình sẽ chạy mãi mãi. Bây giờ câu hỏi thay đổi ... Tại sao GC không tự động được kích hoạt khi lỗi phân bổ? –