Confusión con Recursión

Hola amigos, me cuesta entender el concepto de recursión, en particular, si bien la aplico, no termino de entender exactamente el flujo de una función recursiva.

Voy a intentar explicarlo mejor con código, pongo varias preguntas porque estoy un poco confundido, sepan discupar.

function countdown(n){
  if (n <1){
    console.log(n)
    return [];
    // cuando se cumple la condición retorna un array vacío
    // ese array lo rellenará con el valor del array que retornó la llamada recursiva (creo)
  
} else {    
    const COUNT_ARRAY = countdown(n - 1);
    // la llamada recursiva parece almacenar todas las iteraciones hasta que se cumple la condición del if (las almacena? en un espacio de memoria temporal será?)
   // una vez que completó las iteraciones ¿ejecuta el código posterior?  ¿o lo ejecuta en cada iteración?

    COUNT_ARRAY.unshift(n); // ¿esto se ejecuta cada iteración o se ejecuta todo junto luego?
    return COUNT_ARRAY; // esto se ejecuta aparentemente después del return de parada
  }

}
// Cambia solo el código encima de esta línea

console.log(countdown(15));
// primero ejecuta las iteraciones y después
// pone el return y ejecuta la función (creo)

I’ve edited your post for readability. When you enter a code block into a forum post, please precede it with a separate line of three backticks and follow it with a separate line of three backticks to make it easier to read.

You can also use the “preformatted text” tool in the editor (</>) to add backticks around text.

See this post to find the backtick on your keyboard.
Note: Backticks (`) are not single quotes (’).

Ok, thanks!
I’am new user of this forum, I’m learning to using.

Maybe I should switch to the Spanish forum, what do you think?

No problem being new. We were all there and had to have these things explained.

As to the Spanish forum - it’s up to you. You will probably get more answers in English, but it just depends on your comfort level.

1 Like

Recursion is a very confusing topic for beginners. Heck, a lot of experienced programmers aren’t very comfortable with them, including me. Keep in mind that most programmers (especially web developers) don’t have to deal with recursion much. But with certain types of data, it can be very useful and it does come up on interviews so it is good to know.

I think it is helpful to understand the call stack. When a function call is made, the information about the function call is “pushed” onto the call stack and when the function is complete, it is “popped” off the call stack.

Let’s look at our recursive function.

First we call it with

countdown(15)

Since n<1 is false, we go to the else branch. There we have:

const COUNT_ARRAY = countdown(n - 1);

JS wants to figure out what goes into COUNT_ARRAY so it has to evaluate the right side of that equation. But that is countdown(n - 1), which is basically countdown(14) The current function call (where n=15) can’t complete until this new function call (where n=14) is run and returns something. So, we leave that old function call (n=15) on the call stack (incomplete) and push a new function call on the call stack, the one where n=14. It will run into the same problem. So will n=13, etc.

By the time we get down to n=0, we have 15 incomplete function calls stacked up in the call stack, plus the current one that is running (n=0). When we get to n=0, finally n<1 is true. In recursion, we call this the base condition. Now, finally one of the function calls will finish, will return something. This function call finishes and returns []. That function call has finished so it gets popped off the call stack and control returns to the next one on top of the call stack, the n=1 function call.

Now that we’re in the n=1 call, we can finally evaluate

const COUNT_ARRAY = countdown(n - 1);

because that call (countdown(0)) returned an empty array, that’s what COUNT_ARRAY becomes. Then we unshift n (which is 1) onto it, so it is now [1], which we return that to the next incomplete function call on the call stack.

That is the n=2 call. It goes through the exact same process as the n=1 call, but because [1] got returned, it is assigned to COUNT_ARRAY. Then we unshift n onto it, which is 2. So, we end up with [2, 1] and return that to the next incomplete function call on the call stack.

This continues until all the function calls are “unwound” and we end up with our final result. The weird thing to grasp is that all those function calls are incomplete until we finally reach n=0 and then the whole thing unravels giving us our answer.

I think understanding recursion can be a visual thing. I might suggest checking out some videos.

Again, don’t worry too much if this is confusing. This may be something that takes some time to get a complete understanding. Perhaps consider settling for a partial understanding and work on other things and come back to this from time to time as your understanding grows.

2 Likes

KevinSmith, you it has taken the time and returned a very graphical explanation of recursion. :bulb:

I suspected that those calls were being held in memory until can do it something with these :thinking:, now I understand that this suspicion was referring to the stack.

Im really very thanks for found people as you here, sorry my bad english, I’m learning.

Best regards.
Darío.-

Your English is fine, much better than my Spanish. I’m glad I was able to help.

1 Like

Hola @dariofinelli,

El programa Python Tutor es bastante útil para obtener una visión más detallada de los pasos que se ejecutan en un programa:

https://pythontutor.com/live.html#mode=edit

Cheers and happy coding :slight_smile:

1 Like

Excelente erretres, una explicación gráfica que despeja varias dudas.
Gracias!

1 Like

Thank you sooooo much, this is highly explanatory.

1 Like