The first parameter .map accepts is the callback to run on every iteration.
array.map(item => somethingelse)
is equivalent to
const callback = item => somethingelse;
array.map(callback);
The second parameter .map accepts is the this value to use while running the callback. To illustrate:
const obj = {};
const arr = [0, 1, 2];
const arr2 = arr.map(
function() { console.log(this === obj) },
obj
);
It's usually pretty weird to reference this inside a .map, but it's possible, and by passing a second argument, you can determine what it refers to.
Array.prototype.pop requires a calling context - a this value - to know which array you're trying to pop items from, so in the original code:
reverse=a=>[...a].map(a.pop,a)
a must be passed as a second argument for the .map to work.
a.pop is equivalent to Array.prototype.map here, because it's passed as a callback:
// Equivalent code:
reverse=a=>[...a].map(Array.prototype.pop, a);
The [...a].map( part is being used as a shortcut to invoke .pop() n times, where n is the length of the original array. Each item returned results in a new item in the new array - last item in the original array is popped first and put into the first position in the new array, and so on.