How does the Math.max.apply() work?

2019-01-02 15:41发布

How does the Math.max.apply() work?.

<!DOCTYPE html>
<html>
<head>
<meta charset=utf-8 />
<title>JS Bin</title>
</head>
<body>
  <script>
      var list = ["12","23","100","34","56",
                                    "9","233"];
      console.log(Math.max.apply(Math,list));    
  </script>
</body>
</html>

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Math/max

The above code finds the Max number in the List. Can anyone tell me how does the below code work?. It seems it works if i pass null or Math.

console.log(Math.max.apply(Math,list));

Does all the user-defined/Native functions have call and apply method which we can use?.

5条回答
路过你的时光
2楼-- · 2019-01-02 15:49

apply accepts an array and it applies the array as parameters to the actual function. So,

Math.max.apply(Math, list);

can be understood as,

Math.max("12", "23", "100", "34", "56", "9", "233");

So, apply is a convenient way to pass an array of data as parameters to a function. Remember

console.log(Math.max(list));   # NaN

will not work, because max doesn't accept an array as input.

There is another advantage, of using apply, you can choose your own context. The first parameter, you pass to apply of any function, will be the this inside that function. But, max doesn't depend on the current context. So, anything would work in-place of Math.

console.log(Math.max.apply(undefined, list));   # 233
console.log(Math.max.apply(null, list));        # 233
console.log(Math.max.apply(Math, list));        # 233

Since apply is actually defined in Function.prototype, any valid JavaScript function object, will have apply function, by default.

查看更多
谁念西风独自凉
3楼-- · 2019-01-02 15:52

Math.max(val1, val2,...)

Math.max(1, 2, 3); // Math.max([value1[, value2[, ...]]])
value1, value2... are parameters and must be Numbers MDN Math.max

You can't pass array as Math.max parameters. To pass an array you have to use apply.

Apply

The first parameter of apply is this, the second is array. Math methods are equivalent of static in other languages, which means it doesn't need an object instance unlike to array.prototype.slice so you don't need to pass this in this case.

Example

var arr = [1, 2, 3];

Math.max(1, 2, 3);  // -> 3
Math.max(arr);      // -> NaN (Not a Number)
Math.max.apply(null, arr);  // Math.max.apply(null, [1, 2, 3]) -> Math.max(1, 2, 3) -> 3

arr.slice(1);  // -> returns Array [2, 3]
Array.prototype.slice.call(arr, 1); // Array.prototype.slice.call([1, 2, 3], 1) == [1, 2, 3].slice(1)

When you want to pass an array as parameter you have to use apply, otherwise use call.

apply = array
call = comma separated
More about call & apply

查看更多
心情的温度
4楼-- · 2019-01-02 15:58

Can anyone tell me how does the below code work?

Math.max.apply(Math,list)

Invokes a Math.max function with Math object to be used as a this reference in the function implementation (body) and list to be passed as an arguments.

So this eventually equals to

Math.max("12","23","100","34","56", "9","233")

It seems it works if i pass null or Math.

Obviously Math.max implementation doesn't use instance variable - there is no reason to do so. The naive implementation would just iterate over arguments and find the maximum one.

Does all the user-defined/Native functions have call and apply method which we can use?.

Yes, every single function can be invoked using call or apply

References:

查看更多
若你有天会懂
5楼-- · 2019-01-02 16:04

I will start by saying Math.max(...numbers) and Function.prototype.apply() should only be used for arrays with relatively few elements. (...) and apply will either fail or return the wrong result if the array is too large

Math.max.apply(null | undefined | Math, numbers) is the same as Math.max(...numbers) so I would recommend Math.max(...numbers) for aesthetic reasons.

const numbers = [5, 6, 2, 3, 7];

const max = Math.max(...numbers);

console.log('max:', max);
// expected output: 7

const min = Math.min(...numbers);

console.log('min:', min);
// expected output: 2

If you need to find the maximum element in a numeric array that is very large: use the Array.reduce() method.

Array.reduce() can be used to find the maximum element in a numeric array, by comparing each value:

const numbers = [5, 6, 2, 3, 7];
const getMax = (numbers) => numbers.reduce((a, b) => Math.max(a, b));

const getMin = (numbers) => numbers.reduce((a, b) => Math.min(a, b));
	
const max = getMax(numbers)
const min = getMin(numbers)

console.log('max:', max)
console.log('min:', min)

Conclusion:

Numeric array that is relatively small: use Math.max(...numbers) Numeric array that is very large: use the Array.reduce() method

查看更多
与风俱净
6楼-- · 2019-01-02 16:11

On JavaScript ES6 just use the Spread operator:

var list = ["12","23","100","34","56","9","233"];
console.log(Math.max(...list));
//                   ^^^ Spread operator 
查看更多
登录 后发表回答