mjmitche
mjmitche

Reputation: 2067

JavaScript Math (parameter passing, arrays, and the "apply" method)

1) Why does the function smallest fail? I think it conforms to the example in the Mozilla documentation https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Math/min, which says

 function getMin(x,y) {  //from Mozilla documentation
   return Math.min(x,y)
}



function smallest(array){ //my own experimentation with Resig`s example
  return Math.min(array);
}
function largest(array){      //from John Resig`s learning advanced JavaScript #41
  return Math.max.apply( Math, array );
}
assert(smallest([0, 1, 2, 3]) == 0, "Locate the smallest value.");
assert(largest([0, 1, 2, 3]) == 3, "Locate the largest value.");

Upvotes: 2

Views: 2223

Answers (6)

kennebec
kennebec

Reputation: 104780

apply passes the array to Math.min as an arguments object- Math.min(a,b,c,d,e)

smallest is passing the whole array as the first agument-

Math.min(x) and it really has nothing to compare it to.

Upvotes: 1

Pointy
Pointy

Reputation: 413737

The "Math.min()" function can take an arbitrary number of arguments. However, passing a single array to the function is just passing in one argument, not several. That single argument is the array itself. Arrays, you will recall, are first-rate values.

That's the whole point of the "apply" function that's available on every function. It is used to invoke the function and pass it an argument list composed of entries in an array instance. When you do this:

var array = [ 1, 2, 3, 4, 5 ];
someFunction.apply(irrelevant, array);

that's like calling:

someFunction(1, 2, 3, 4, 5);

(The "irrelevant" argument is what's to be used as the this value in the function call.)

Upvotes: 5

SilverbackNet
SilverbackNet

Reputation: 2074

.apply( object, array ) is the correct syntax to unpack an array into an argument list. Just passing an array to a function that converts all arguments to a number isn't useful, since it will only see NaN.

Upvotes: 1

joelt
joelt

Reputation: 2680

It doesn't conform to the example. The []'s in the documentation are optional indicators, not array delimiters.

Upvotes: 2

C. K. Young
C. K. Young

Reputation: 223043

Math.min and Math.max takes any number of numbers, as arguments. Your smallest is trying to pass an array, not numbers.

The use of apply (as in largest in your example) pastes the elements of the array as arguments.

Upvotes: 3

Mike Samuel
Mike Samuel

Reputation: 120516

Try

function smallest(array) { return Math.min.apply(Math, array); }

It won't work when passed as an array because min converts its arguments to numbers before comparing. Trying to convert an array to a number will, unless the array contains a single element that looks like a number, produce NaN.

So

Math.min([3]) === 3
Math.min('3') === 3

but

isNaN(Math.min([3, 4]))  // because,
isNaN(Math.min('3,4'))  // which is the same as
isNaN(Math.min(+'3,4'))  // which is equivalent to
isNaN(Math.min(NaN))

Upvotes: 1

Related Questions