A pedantic would note that lines 24 and 27 do use arithmetics operators.
Anyway, have you ever used
abacus?
https://en.wikipedia.org/wiki/Abacus
The sum() behaves like abacus. At first you have n and m beads.
Then, on each step, you remove one bead from n and add one bead to m, until n has no beads left.
There will be n steps, because you can take only that many beads from n.
In n steps, n beads are added to the m (one by one). Thus, at end, the latter lot has m+n beads.
There is a loop version of the same:
1 2 3 4 5 6 7
|
int sum( int n, int m ) {
while ( 0 < n ) {
--n;
++m;
}
return m;
}
|
Arithmetics says:
(n + m) == (n-1 + m+1) == (n-2 + m+2) == ... == (0 + m+n) |
When your main() calls sum(n,m), the function calls itself recursively, until a call
sum( 0, x )
is made, (where x==n+m). That call returns x to the caller (line 32).
Where is the call? On line 34. What is done with the returned value? It is returned as is into the caller of this instance. I.e. the call to sum() that does call sum(0,x) does receive value x and does return it to its own caller. The chain of returns returns from the recursion and thus the main() receives x.
Similarly:
(n * m) == ( ((n-1)*m) + m) == ( (((n-2)*m) + m) + m) |
The recursive prod() does in effect expand the multipication into many additions, and then uses the sum() to evaluate it.