^^ Trebuie să înțelegi ce se întâmplă în culise atunci când se apelează o funcție. Să considerăm că funcția noastră este una simplă :
- int suma(int a, int b){
- int c;
- c = a + b;
- return c;
- }
Apelând funcția prin :
se vor întâmpla 3 lucruri :
- Se va aloca spațiu pe stivă pentru a găzdui atât parametrii funcției cât și variabilele locale declarate în ea + adresa de revenire după terminarea apelului.
- Se vor inițializa parametrii a cu 1 și b cu 2
- Se va trece la execuția codului ce-l conține funcția
Grafic, situația s-ar prezenta în felul următor :

Distingem 4 momente (prefixate cu "
t = ") importante pe parcursul acestei execuții :
- Momentul 0 : apelul inițial de funcție
- Momentul 1 : alocarea de spațiu pe stivă (cel discutat mai sus)
- Momentul 2 : terminarea funcției
- Momentul 3 : golirea stivei de valori utilizate în cadrul funcției și returnarea la punctul din care s-a declanșat apelul
Dacă acest aspect este clar, vom continua cu cazul tău concret,
sharky92. În acest cadru, vom elimina bucăți de cod nefolositoare explicației și vom prezenta, în același spirit, situația stivei pentru un apel recursiv. Generalizarea rămâne la latitudinea imaginației tale, dar nu este un lucru foarte dificil.
Pornim, așadar, cu codul ciopârțit :
- int divide_et_impera(int p, int q)
- {
- int mij,max,max2;
- ...
- max=divide_et_impera(p,mij);
- ...
- return ...
- }
Se poate ușor observa că avem relativ aceleași elemente ca și în prima explicație și anume : avem o funcție (?!?), avem parametri (chiar același număr și același tip) și avem și variabile locale. Pe lângă acestea, mai avem și un apel la sine. Să vedem cum se comportă stiva în această situație :
[Dacă nu se vede complet, deschide imaginea într-o filă nouă]După cum se poate intui, se observă un comportament asemănător.
Analizăm din nou timpii cheie :
- 0 : se realizează apelul inițial
- 1 : stiva inițială este alocată comform principiului de mai sus
- 2 : la un moment dat, in cadrul funcției, avem un apel la ea însăși. În acest moment, se împing pe stivă un alt spațiu necesar funcției susținând acum un total de 2 adrese de returnare, 2 x p, 2 x q, 2 x [orice].
- 3 : apelul recursiv poate continua alocând tot mai multe spații pe stivă
- 4, 5 : la un moment dat, datorită instrucțiunii de control (if-ul acela), ciorchinele colapsează și se revine, din return în return până la suprafața stivei (momentul în care s-a găsit stiva înainte de primul apel al funcției)
- 6 : terminându-se și acest nivel, stiva este complet curățată, iar calculele sunt îndeplinite, execuția programului reluându-se de la instrucțiunea imediat următoare apelului inițial
Și cam asta este tot. Te rog observă că dacă nu există o instrucțiune de control, se poate ajunge la un moment dat la un număr atât de mare de alocări de funcție pe stivă încât programul rămâne fără memorie. Acest lucru se poate materializa printr-un "Don't send" clasic urmat, uneori, de un bine plasat upercut de "End Task".
Spor