array.filter() 删除函数表达式中的 <falsey> 值,但不删除箭头函数中的值

array.filter() removes <falsey> values in a function expression but not in arrow function

我正在解决一个问题,其中数组 a 中的函数 array_diff returns 值也在数组 b.

因为我一直在学习命名函数表达式比匿名胖箭头函数更适合控制台调试,所以我试图用命名 removeDuplicate 函数来过滤我的数组来解决这个问题。

但是,我无法阻止过滤器函数从我返回的数组中自动删除错误值 0。

命名函数表达式:

function array_diff(a, b) {
  return a.filter(function removeDuplicate(x) { if(b.indexOf(x) == -1) return x; });
}

array_diff([0,1,2,3,4],[2,4]); // [1, 3]

匿名胖箭函数:

function array_diffTwo(a, b) {
  return a.filter((x) => { return b.indexOf(x) == -1 });
}

array_diffTwo([0,1,2,3,4],[2,4]); // [0, 1, 3]

有人可以向我解释为什么在 array_diff 而不是 array_diffTwo 中删除了虚假值 0 吗?

问题是您 return x 来自过滤器回调。如果 x(被迭代的项目)为假,结果将不会包含在最终数组中,即使 b.indexOf(x) == -1 测试已完成。

用下面的代码做同样的事情:

return b.indexOf(x) == -1

function array_diff(a, b) {
  return a.filter(function removeDuplicate(x) { return b.indexOf(x) === -1 });
}

console.log(array_diff([0,1,2,3,4],[2,4])); // [0, 1, 3]

(附带说明,您没有在代码中的任何地方使用箭头函数)

您可以通过创建一组 b 来将计算复杂度从 O(n ^ 2) 降低到 O(n),而不是在每次迭代时检查 indexOf

function array_diff(a, b) {
  const bSet = new Set(b);
  return a.filter(function removeDuplicate(x) { return !bSet.has(x); });
}

console.log(array_diff([0,1,2,3,4],[2,4])); // [0, 1, 3]

你误解了 array.filter(callback)。 callback 应该是一个谓词,在回调中你 return true 用于你想要保留的元素,false 用于元素,not the element。当您 return 元素本身时,这就是删除虚假元素的原因。

另外,箭头函数应该是这样的

array_diff =(a,b)=>a.filter(x=>b.indexOf(x)<0)
console.log(array_diff([0,1,2,3,4],[2,4]))