Bir süreç (process) başladığı anda boş bir bellek yeri bu süreç için ayrılır. Buna “Managed Heap” denir. (Devamında heap bellek olarak belirteceğim ) Pointer’lar aracılığıyla heap bellekten nesnelerin yerleri tutulur. Çalışma zamanında oluşturulan nesneler, uygulama tarafından ihtiyaç duyulmadığı zamanlarda, heap bellekten temizlenir. Bu işlem için “Garbage Collector” mekanizması kullanılır.
Uygulama “new” operatörünü çalıştırdığı zaman “heap” belleğe gider ve yeterli bir yer olup olmadığına bakar. Yeterli yer varsa “pointer heap” bellekteki bu yeri gösterir, nesnenin “constructor” metodu çalıştırılır ve adres döndürülür.
Peki, bu yer doluysa uygulama ne yapar?
İşte bu anda “Garbage Collector” devreye girer ve uygulamanın ihtiyaç duymadığı tüm objeler “heap” bellekten temizlenir.
“OutOfMemoryException”: Temizlenecek obje yoksa ve yeterli yer hala sağlanamamışsa “new” operatörü “OutOfMemoryException” uyarısını verir.
“Garbage Collector” Nasıl Çalışır?
Her uygulama başlarken bellekte bir yer ayırdığını belirtmiştik. Burayı gösteren ilk adres bizim uygulamanın başlangıç noktasıdır. Bir uygulama için birden çok başlangıç noktası mevcuttur. “Static” veriler için bir başlangıç noktası, “cpu register”ları için bir başlangıç noktası gibi.
“Garbage collector”, “heap” bellekteki her şeyi temizlenecek nesneler olarak algılar ve bir başlangıç noktasından başlayarak tüm nesneleri kontrol eder ve bir “graph” oluşturur. Bu başlangıç noktasındaki tüm nesneleri kontrol edip “grap” oluşturduktan sonra diğer başlangıç noktasına geçer ve oradaki tüm nesneleri kontrol eder.
“Garbage collector” çok akıllı bir algoritmaya sahiptir. Örneğin, diyelim ki herhangi bir nesne iki başlangıç noktasında da var. “Garbage collector” bu nesneye geldiği zaman bu nesneyi zaten “graph”a eklemiş olduğunu anlar ve bu nesnenin altındaki nesneleri kontrol etmez. Böylece daha hızlı çalışmasını sağlar ve sonsuz döngüye girmesini engeller.
Tüm başlangıç noktalarını ve nesneleri kontrol ettikten sonra oluşan “graph”ı “liner” şekilde kontrol ederek tek tek “heap” belleğe yeniden yerleştirir, aralıklı olanlar varsa bu aralığı da kaldırır. Nesnelerin yeni adresleri olmuşsa bu adresleri gösteren “pointer”ların yeni adresi göstermesini de sağlar. İşlem sonunda gereksiz olan nesneler “heap” bellekten temizlenmiş olur.
Yeniden göz atacak olursak, “new” operatörü çağrıldı, uygulama “heap” belleğe gitti ve yer olmadığını anladı. “Garbage Collector” devreye girdi ve istenen yer ayarlandı. Uygulama “new” operatörünü tekrar çalıştırarak işleme devam eder.
“Garbage Collector”un çalışmasını kısaca özetleyecek olursak, “heap” belleğimizde yer lazım fakat uygun yer yok. “Heap” belleğimiz dolu. O zaman “garbage collector” devreye girer.
“Generations”: “Garbage Collector” algoritması gördüğümüz gibi arka planda birçok iş yapmakta. Peki, bunu daha efektif bir hale nasıl getirebiliriz sorusunun cevabı burada “Generations”.
“Garbage Collector” bu mantık ile bazı kurallar tanımlar.
- Yeni oluşturulan nesnelerin yaşam süresi daha kısadır.
- Eskiden oluşturulmuş nesnelerin yaşam süresi daha uzundur.
- Yeni oluşturulmuş nesneler birbirleriyle daha sıkı bir ilişki içindedir ve kullanım zamanları çok yakındır.
- “Heap” bellekteki bir bölüme ulaşmak, tüm “heap” belleği dolaşmaktan daha hızlıdır.
Şimdi çalışma mantığına bakalım.
- Uygulama çalıştırıldığında “heap” bellek boş olarak oluşturulur.
- Dolduğunu varsayalım ve “Garbage Collector” gelip gereksiz nesneleri temizledi. Bu ilk temizlemede, temizlenmeyen, yani sağ kalan tüm nesneleri “Generation 0” olarak tanımlar.
- Tekrardan doldu ve yine GC çalıştırıldı. “Generation 0”dan sağ kalanları “Generation 1” olarak tanımlar ve yenilerden sağ kalanları da “Generation 0” olarak tanımlar.
- Yine doldu ve yine GC çalıştırıldı. “Generation 1”den sağ kalanları “Generation 2” olarak tanımlar ve “Generation 0”dan sağ kalanları “Genaration 1” olarak tanımlar. En yenilerden sağ kalanları “Generation 0” olarak tanımlar.
- GC çalıştırıldığı zaman sadece belli bir bölgeyi tarama işlemi yapabilir. Yani çalıştırıldı diyelim, tüm “heap” belleği kontrol etmek yerine ilk önce “Generation 0”a gelip bakar, buradaki gereksiz nesneler silindikten sonra yeterli yer sağlanmışsa işlemi bitirir. Diyelim ki bu işlemden sonra hala istenen yer bulunamadı. O zaman “generation 1”i de kontrol eder. Yine olmadıysa “generation 2”yi de kontrol eder. Gördüğünüz gibi kademeli olarak kontrol etmiş olduk. Performans açısından bize olumlu sonuçlar verir.
void GC.Collect (Int32 Generation)
void GC.Collect()
void GC.Collect()
Finalization: Bir diğer özellik de “finalize” metodu. Sınıflarda bu metodu “override” ederek daha sağlıklı ve garantili bir temizleme işlemi gerçekleştirebiliriz. “Garbage Collector” bu nesneyi temizlemek isteyince, ek olarak “finalize” metodunu da çalıştıracaktır. Böylece istediğimiz işlemleri de yapmış olacaktır.
- Belleğe eklenme süresi daha uzundur.
- “Cpu” ekstradan daha fazla kullanılmış olur.
- “Generation” olarak eski olarak tanımlanır ve bu nesneyi direk veya dolaylı olarak gösteren nesneler de bu şekilde etkilenmiş olur.
- “Finalize” metodu çalıştırıldığı zaman bu metoda erişim yapılamaz.
Bazen uygulama kapatıldığı halde “heap” bellekteki bazı nesnelere erişim sağlanabilir, bu da bu nesnenin bir “thread” ya da başka bir süreç tarafından kullanılması ile olabilir ya da uygulama kapanırken bazı nesneleri oluşturabilir. Bu nesnelerin “finalize” metotları çalıştırılmamış olacak ve istediğiniz temizleme işlemi gerçekleşmeyecektir.
Bir diğer durum da, bir nesne başka bir nesneyi gösteren “pointer”a sahip ve bu ikisi de “finalize” metoduna sahip. İçteki nesnenin “finalize”ı önce çalışabilir ve istenmeyen sonuçlar doğurabilir. O yüzden içteki nesnenin “finalize”ına erişimin engellenmesi önerilen bir çözümdür.
“Finalize” metodu kullanılması gerekiyorsa, çok hızlı çalışabilecek bir şekilde tasarlanması önerilen bir diğer çözümdür.
“Dispose” Metodu”: “Dispose” metodu çağrıldığı zaman, nesnenin tutmuş olduğu kaynakları serbest bırakır. Bu metodun birden fazla çağrılması “exception” hatasını döndürür. Örneğin, zaten kaynakları serbest bırakılmış bir nesneye tekrardan “dispose” metodunu kullandırmak gibi.
Hiç yorum yok:
Yorum Gönder