Am înțeles abia azi că mă fascinează colectarea gunoiului deși o simțeam de multă vreme. Azi, pe stradă venind de la casieria RDS, mi-am formulat-o explicit. Uite la ce poate fi bun să nu plătești facturile online și să preferi mersul pe jos celui cu mașina – îți vin pe drum tot felul de idei tîmpite. Imediat după formulare a urmat și infantilul “DE CE”.
Așadar de ce mă fascinează colectarea gunoiului?
(pentru non-specialiști mă refer la o tehnică de recuperare a memorie care nu mai e folosită în sistemele cu management automat al memoriei)
Haideți să împărțim programatorii în două “școli de gîndire” (să-i zicem taxonomie ca să ne bage Google în seamă):
- programatorii pentru care un boolean și un fir de execuție au greutate “mintală” complet diferită (noi);
- programatorii pentru care un boolean și un fir de execuție sînt oarecum, într-un fel, dacă vrei neapărat să spui așa, doar niște chestiuni puțin diferite (ei).
De dragul simplificării (pentru că știm cu toții că programarea nu e decît managementul complexității) și al alocării judicioase a resurselor vom spune din start că povestea se adresează mai ales programatorilor din categoria unu, adică nouă, și nu se adresează direct categoriei doi, adică lor. Așadar programatori din categoria 2: release lock – la masă!
(am eficientizat puțin treaba, sîntem mai paraleli acum: noi cu treaba noastră, ei cu treaba lor)
Dacă ești un programator care a văzut deja destule lucruri și înțelegi cam cît costă gesturile tale de fiecare zi, poți să dormi deja liniștit în C++, surprize în 2010 pot apărea foarte rar. Sigur – asta se plătește cu prețul faptului că ai grijă direct și personal de gunoiul propriu (o treabă deloc de invidiat).
Dacă ești un programator care a văzut deja destule lucruri și înțelegi cam cît costă gesturile tale de fiecare zi (mă repet?), poți avea mari surprize cînd vine vorba de managementul automat al memoriei. Faci totul bine și rezultatul iese prost. Știi cît costă fiecare alocare, fiecare conversie de tip, știi să ții datele localizat, știi exact pînă și cîtă memorie ocupă un decimal ;-) și în final codul merge cumplit de prost. Nu pe masă cînd îl testezi ci în producție, cînd e stresat o perioadă mai lungă. Ăsta e prețul pe care îl plătești tu după, e echivalentul prețului pe care l-a plătit programatorul din C++ cînd a avut atîta grijă să-și curețe frumos tot gunoiul, preț pe care încă îl plătește cînd află că are încă un bug nou pe o cale de cod mai rar bătătorită, unde a dat iar cu oiștea în gard dealocînd prematur sau poate repetat.
Programatorul de C++ își fixează rapid bug-ul și sistemul lui reîncepe să funcționeze exact cum se aștepta, footprint previzibil în memorie, timpi previzibili petrecuți de procesor prin diverse cotloane (pînă ajunge iar pe o altă alee rar bătătorită). Dacă știe meseria, programatorul C++ poate scrie cod complet previzibil (doar atît că orice greșeală îi va fi fatală).
Tu – om cocoloșit, cu gunoiul colectat automat, dacă ai făcut totul corect poți spera ca programul în final să meargă bine. Dacă e un program desktop și utilizatorul are multă memorie, aproape sigur nu vei avea vreodată mari probleme. Pe servere lucrurile pot sta mult mai prost, ele nu au timp să aștepte indulgent, așa cum ar aștepta utilizatorul după editorul de bloguri sau VS.NET să-și colecteze gunoiul. Pe server lucrurile merg pe bandă, gata unu vine altu’. Atunci cînd nu ți-a ieșit treaba cu colectarea, rezultatele arată cam așa: foarte mult timp serverul adună gunoi în loc să facă treabă. Foarte multe colectări de gunoi durează foarte mult și sînt ineficiente. Dacă multe colectări sînt ineficiente, “inexplicabil” gunoiul se adună mai rar dar e nevoie de memorie deci… GC.Collect!!! Foarte mult locking – cînd se adună gunoiul lucrurile nu prea merg bine paralel. Ce bine era în C++…
Cînd lucrurile merg ca mai sus, vinovat e .net că e prost. Uiți comod că te-a scutit de toate coșmarurile bietului programator C++ și vrei ca știind tot ce știe el dar nefăcînd tot ce face el și neriscînd tot ce riscă el, să meargă totul bine. Aiasta nu se poate.
Tu trebuie să știi altceva: nu cînd să dealoci – asta ar fi prea ușor și inutil din moment ce tot rostul colectării automate e să nu dealoci explicit – ci cum să scrii întregul cod așa încît colectarea gunoiului să se petreacă eficient. Asta nu e o tehnologie care să țină de atenție sau grijă așa cum e în cazul C++, e aproape o magie cu reguli vagi, cu logică neimediată, foarte dependentă de implementarea sistemului de colectare, de stilul de programare, de “pattern”-uri (jur să nu repet cuvîntul ăsta vreodată în blog!) – de șabloanele prin care te exprimi cînd scrii cod, de aranjarea “în pagină” a noțiunilor cu care lucrezi, de cum alegi să rezolvi problema, de problema însăși, chestiuni ezoterice comparativ cu “am uitat pe else-ul ăla un free()”.
Asta face treaba fascinantă pentru mine: nu se poate învăța mecanic. Deși are sensuri 100% logice, ele pot fi adînci. Cred că e genul de lucru la care nu e bine să fii expus prea de tînăr pentru că pierzi sensul realității, e bine să vină cînd știi să te ții bine pe picioare altfel te depășește cu mult și așa va rămîne pentru totdeauna, ca și acuzativul sau conjugările (încă un motiv pentru care Java de tînăr poate dăuna grav competenței). E tipul de lucru care se face de obicei pe bază de tradiție. Dacă vrei să treci de nivelul ăsta începe să fie nevoie de multe multe… conexiuni.
Am doua observatii:
primo: iti propun sa inlocuiesti „taxonomie” prin „taxinomie”, nu de alta, dar e mai putin folosit si suna si mai pretios ca prima varianta
secundo: dupa „pentru că știm cu toții că programarea nu e decît managementul complexității”, am inteles pe propria-mi piele pozitia ta fata de „trebuie” si derivatele lui: „logic!”
bineinteles, ca facind parte din a doua categorie (prin extensie, caci nici macar nu sunt programator), dupa indemnul tau, m-am dus la masa!
la secundo: trebuia sa pun acolo un „nu-i asa?” si un link la surprize-surprize dar m-am luat cu vorba si am uitat.
nu stiu de ce ai bineinteles-o ca faci parte din categoria 2. era vorba de taxi legat de programatori :) neprogramatorii nu se dau cu acest taxi deci nu te include unde nu-ti fierbe oala! imediat ai gasit un motiv sa te duci la masa…