Un colector de gunoi (GC) este un manager de memorie. Multe limbaje de programare au un GC încorporat. Această caracteristică alocă și dealoca automat memoria într-un program. Eliberează memoria blocată, nefolosită, care încetinește aplicația.

Frumusețea unui GC este că eliberează memorie în numele tău, fără să fii nevoie să faci nimic. Prin urmare, ați putea să o considerați o caracteristică atât de esențială încât v-ați aștepta ca fiecare limbaj de programare să o aibă. Din păcate, acesta nu este cazul; chiar și unui limbaj popular precum C poate lipsi un GC.

Cum funcționează alocarea memoriei?

Când rulați un program în orice limbaj de programare, sistemul dvs. de operare își rezervă a stiva de date în memorie pentru acel program. Acest program deține și ocupă această stivă de date până când încheie execuția. Dacă programul dvs. are nevoie de mai multă memorie decât cea disponibilă, poate aloca în mod dinamic mai multă memorie din heap-ul de memorie al sistemului de operare.

În programare, o variabilă reprezintă o locație de memorie. Deci, atunci când declarați o nouă variabilă, limbajul de programare alocă spațiu în memorie pentru această variabilă. Variabila va avea acum o adresă de memorie. Până când nu alocați o valoare acestei variabile, aceasta va rămâne neinițializată și ar putea conține o valoare necorespunzătoare.

Dacă un limbaj de programare vă permite să declarați o variabilă fără a o inițializa, atunci este o variabilă dinamică. Aceasta înseamnă că valoarea pe care o atribuiți variabilei se poate schimba în timp. Cu toate acestea, locația de memorie a variabilei va rămâne aceeași până când o dealocați.

Cum funcționează dealocarea memoriei?

Alocarea memoriei este un proces similar pentru toate limbajele de programare. Dar metoda corespunzătoare de dealocare a memoriei tinde să difere. Există două tipuri de metode de dealocare a memoriei; manuala si automata. Un GC face dealocarea automată.

Dealocarea memoriei fără un colector de gunoi

The limbaj de programare C nu folosește un GC pentru dealocarea memoriei. Prin urmare, programatorii C trebuie să aloce și să dealocați manual memoria. C permite alocarea dinamică a memoriei atunci când nu știți, în momentul compilării, câtă memorie veți folosi în timpul rulării.

Biblioteca standard (stdlib.h) conține funcțiile pe care C le folosește pentru a gestiona alocarea dinamică a memoriei. Aceste funcții includ:

  • malloc(): alocă o anumită dimensiune a memoriei și returnează un pointer către acea memorie. Dacă nu există suficientă memorie disponibilă în pool-ul de memorie al sistemului de operare, returnează null.
  • free(): dealoca un anumit bloc de memorie și îl returnează în pool-ul de memorie al sistemului de operare.

C Exemplu de program

#include
#include

intprincipal()
{
int *ptr; // declar pointerul
int j; // declara counter

// alocă spațiu pentru 200 de numere întregi
ptr = (int *) malloc(200 * dimensiunea(int));

// introduceți valori întregi în memoria alocată
// și imprimă fiecare valoare în consolă
pentru (j = 0; j < 200; j++)
{
ptr[j] = j;
printf("%d\t",ptr[j]);
}

// dealocarea memoriei alocate anterior
gratuit(ptr);
întoarcere0;
}

Codul de mai sus alocă memorie pentru a stoca 200 de valori întregi folosind malloc() funcţie. Folosește un pointer pentru a accesa această locație de memorie și stochează 200 de valori întregi în ea. Pointerul imprimă, de asemenea, datele stocate în locația de memorie pe consolă. În cele din urmă, programul dealoca memoria alocată anterior utilizând gratuit() funcţie.

Dealocarea memoriei cu un colector de gunoi

Mai multe limbaje de programare populare folosesc un GC pentru gestionarea memoriei. Acest lucru face viața programatorilor care folosesc aceste limbaje mult mai ușoară. C# și Java sunt două limbaje de programare care folosesc un GC.

C# GC

În Limbajul de programare C#, un GC gestionează alocarea și dealocarea adreselor de memorie. Prin urmare, un programator C# nu trebuie să-și facă griji cu privire la dealocarea unui obiect după ce își finalizează scopul.

C# GC inițializează un pool de memorie, numit heap gestionat, pentru fiecare proces (sau program) nou. Se numeste VirtualAlloc() funcția de alocare a memoriei și VirtualFree() funcția de dezalocare. Cea mai bună parte este că toate acestea se întâmplă în fundal, fără a fi nevoie de niciun efort din partea dvs., programatorul.

C# GC are un motor de optimizare, pe care îl folosește pentru a decide când să dealocați memoria. Motorul de optimizare examinează rădăcina aplicației pentru a determina ce obiecte nu mai sunt utilizate. Face acest lucru prin crearea unui grafic care se extinde de la rădăcina aplicației până la obiectele conectate. Această rădăcină include câmpuri statice, variabile locale etc. Orice obiect care nu este conectat la rădăcina aplicației este gunoi.

Motorul de optimizare GC nu doar colectează memorie pe cont propriu. Mai întâi trebuie să existe o nouă cerere de alocare a memoriei. Dacă sistemul are o cantitate mică de memorie disponibilă, atunci motorul de optimizare GC va intra în joc.

GC Java

În Java, un GC gestionează, de asemenea, alocarea și dealocarea adreselor de memorie. Cu toate acestea, Java are în prezent patru tipuri diferite de colectoare de gunoi acceptate:

  • Garbage-First (G1)
  • Serial
  • Paralel
  • Z Garbage Collector (ZGC)

Colectorul de gunoi G1 este GC implicit al Java de la lansarea Java Development Kit (JDK) 9. Java organizează datele în obiecte și stochează aceste obiecte într-un heap de dimensiuni fixe. Colectorul de gunoi G1 împarte heap-ul în regiuni de heap de dimensiuni egale. Apoi a împărțit aceste regiuni heap în două secțiuni; generațiile tinere și bătrâne.

De fiecare dată când creați un obiect nou, alocarea spațiului pentru acest obiect are loc în generația tânără. Folosind un proces de îmbătrânire, colectorul de gunoi G1 copiază obiectele din regiunile tinere în regiunile vechi. De asemenea, copiază obiectele care se află deja în regiunea veche într-o regiune mai veche.

Colectorul de gunoi G1 efectuează apoi cea mai mare parte din dealocarea memoriei în generația tânără, aventurându-se ocazional în secțiunea generației veche.

Care sunt beneficiile de a avea un colector de gunoi?

Avantajul de a avea un colector de gunoi este că vă împiedică să vă gândiți la gestionarea memoriei în timp ce scrieți codul. Acest lucru vă oferă timp să vă concentrați asupra celorlalte aspecte importante ale aplicației dvs. Cu toate acestea, mai multe alte beneficii merită subliniate.

Recuperarea obiectelor neutilizate și eliberarea memoriei asigură o execuție mai curată a aplicației. Dacă programul dvs. eliberează memorie cât mai curând posibil, acesta va avea o amprentă de memorie mai mică și va putea rula mai eficient.

Colectarea gunoiului reduce erorile legate de gestionarea memoriei, cum ar fi scurgerile și erorile de indicator. Acest lucru se datorează faptului că procesul nu mai depinde de programator și de capacitatea acestora de a scrie cod precis.