I understand recursive functions generally and have written them myself to solve problems, but this one confused me. On each call, the function returns 1 + sumAll([first + 1, last]) but what is the value of sumAll([first + 1, last])? Since all it does is check for a condition and if the condition is not reached, it repeats the above operation.
function sumAll(arr) {
const [first, last] = [...arr].sort((a, b) => a - b);
return first !== last
? first + sumAll([first + 1, last])
: first;
}
sumAll([1, 4]);
Thanks, yes I meant 1 in this example in particular. Can you point me to the line of code that gets the sum of numbers between first + 1 and last? I just don’t see it.
I still don’t understand. On the second call, the function returns 1 + sumAll([2, 4]), but isn’t the result of sumAll([2, 4]) just 2 + sumAll([3, 4]), then 3 + 4 on next call which gives 7, and that is not the correct answer, because it should give 10. I wrote a recursive function that makes more sense to me and it passes the test, but I would still like to understand the one above.
function sumAll(arr, stop = 0, [first, last] = [...arr].sort((a, b) => a - b), [copyFirst, copyLast] = [...arr].sort((a, b) => a - b), acc = copyFirst) {
if (stop === copyLast - copyFirst) {
return first
} else {
acc++
first = first + acc
stop += 1
console.log(first)
return sumAll(arr, stop, [first, last], [copyFirst, copyLast], acc)
}
}
console.log(sumAll([1, 4]));
I tried that. I don’t understand why the value of sumAll([3, 4]) is 7. As far as I understand the function never returns a number unless first === last so wouldn’t the result of sumAll([3, 4]) be 3 + 4? 3 being first and 4 being the result of sumAll([4, 4])
Wait I just confused myself. I just said I didn’t understand why sumAll([3, 4]) is 7 and then went ahead and said it would equal 7. I need to step back for a minute here lol
The solution is your original post is terse. Are you familiar with ternaries? This is the code written less tersely.
function sumAll(arr) {
const [first, last] = [...arr].sort((a, b) => a - b);
if (first !== last) {
// recursive case
return first + sumAll([first + 1, last]);
} else {
// base case
return first;
}
}
sumAll([1, 4]);
Here:
first + sumAll([first + 1, last]);
you are calling the function. That function call has to complete before the current function call can return a result.
Here you are accumulating all of the data down into a single function call:
but that sort of dodges the bits about function calls, scope, and return values that can make recursion tricky. It’s those bits that seem to be confusing you the most about the solution in the first post.
I really appreciate your help but the issue is not the ternary statement, I understand those completely and use them myself, it’s the recursive case in that function that I don’t get. I tried running it on python tutor but I still don’t get it. Thanks for your time though.
The function call sumAll([1, 4]) returns 1 + sumAll([2, 4]), right? But what is sumAll([2, 4])?
The function call sumAll([2, 4]) returns 2 + sumAll([3, 4]), right? But what is sumAll([3, 4])?
The function call sumAll([3, 4]) returns 3 + sumAll([4, 4]), right? But what is sumAll([4, 4])?
The function call sumAll([4, 4]) returns 4.
Therefore, the function call sumAll([3, 4]) returns 3 + 4 === 7, right?
Therefore, the function call sumAll([2, 4]) returns 2 + 7 === 9, right?
Therefore, the function call sumAll([1, 4]) returns 1 + 9 === 10, right?
This is the exact set of steps presented by pythontutor, converted to words. You cn also create something similar by using console.log() inside of the function.
Just to try and give you one more analogy for how it works (hopefully without causing more confusion). You remember order of operations from algebra class all those years ago? The way I was taught was PEMDAS (parentheses, exponents, multiplication, division, addition, subtraction). Parentheses take the most precedence, so you need to solve the chunks within parentheses first.
In terms of a math equation, the call to sumAll([1, 4]) looks like this:
1 + (2 + (3 + (4)))
Following order of operations we need to start from the innermost parentheses (the recursive calls in this analogy):
// 4 is just 4
1 + (2 + (3 + 4))
// 3 + 4 is 7
1 + (2 + 7)
// 2 + 7 is 9
1 + 9
10
In terms of English this could be phrased as
The sum of integers from 1 to 4 is equal to
1 plus the sum of integers from 2 to 4, is equal to
1 plus 2 plus the sum of integers from 3 to 4, is equal to
1 plus 2 plus 3 plus the sum of integers from 4 to 4, is equal to
1 plus 2 plus 3 plus 4… so 10