i have this two recursive functions in javascript.
first function returns digits of the input number in right to left order
second function returns them in left to right order.
function first(n){
if(n > 0){
m = Math.floor( n/10 );
v = ( n - m * 10 ) + " " + first(m);
return v;
}
return "";
}
function second(n){
if(n > 0){
m = Math.floor( n/10 );
v = second(m) + " " + ( n - m * 10 );
return v;
}
return "";
}
result of the first function is
7 6 1
result of the second function is
1 16 167
but I expected this
1 6 7
I tested similar code in PHP and JAVA and it works well.
Presumably the problem is in Javascript's closures. But I cant figure how to fix it.
It's perfectly simple: You're using implied globals:
function second(n)
{
if(n > 0)
{
m = Math.floor( n/10 );
//m is changing here ------\\will use lowest value of m
v = second(m) + " " + ( n - m * 10 );
return v;
}
return "";
}
The fix is:
function second(n)
{
if(n > 0)
{
//make declare it in the scope itself
var m = Math.floor( n/10 );
v = second(m) + " " + ( n - m * 10 );
return v;
}
return "";
}
This still leaves you with the evil implied global v
, too. If I were you, I'd declare v
locally, too
function second(n)
{
var m, v = '';
n = +(n);//coerce to number
if (n > 0)
{
m = Math.floor(n/10);
v = second(m) + ' '+ (n-m*10);
}
return v;
}
This function works as expected.
The problem didn't really have to do with closures as such, but it was caused by the way JS resolves expressions/names.
Couple that to how JS deals with recursive functions and you get the output you got, plain and simple.
JS doesn't really have a recursive call-stack, yet. Last time I checked, recursive calls were effectively short-circuited (~= goto's). I remember reading something on the subject by Douglas Crockford, about it having something to do with the call-stack.
Though ES5's strict mode does introduce TCO, and it should make it by the end of 2013 (ES6 - Harmony). I've linked to a couple of sites here, if you care to read more on the matter