有没有一种简单的方法可以在不使用参数的情况下将给定数组的全部内容快速传递到“Array.prototype”方法变量中?

Is there a simple way to quickly pass the entire contents of a given array into an `Array.prototype` method variable without using parameters?

上下文

我创建了一个数组 docket 来跟踪用户单击 canvas space 时的坐标。在主程序循环期间,数组将由绘图函数扫描,以便可以看到选定的像素。最初,在我的事件侦听器中,我使用的是 push( ) 方法,但后来我意识到我想要一种切换像素的方法。

代码说明

所以我向 Array.prototype 添加了一个方法 poke( ),如下所示,它允许我将整个 docket 数组推入本地数组 param.array 并赋值触发坐标到局部变量 param.entryentry 然后被推入 array 并且 array 由主 poke( ) 循环处理以确保没有重复值。如果找到匹配项,则两个元素都被消灭并且 param.array 被 return 到顶部,最终将 docket 缩小 1;如果没有找到匹配,则没有元素被消灭,param.array 被 returned 到顶部,最终将 docket 扩展 1.

主要问题:示例 1

反正现在写的方法,必须这样调用:

docket.poke( docket, e.key ); 注意:为简单起见,我使用了键盘键值。

Array.prototype.poke = function( a, b ) {
  var bool = {  },  i = {  },  param = {  };
  param.array = a;  param.entry = b;    
  //
  param.array.push( param.entry );
  i.len = param.array.length;
  i.end = i.len - 1;
  //
  for ( i.cur = 0; i.cur < i.len; i.cur++ ) {
    bool.match = param.array[ i.cur ] == param.array[ i.end ];
    bool.nSelf = !( i.cur == i.end );
    //
    if ( bool.match && bool.nSelf ) {
      param.array.splice( i.end, 1 );
      param.array.splice( i.cur, 1 );
      //
      i.end -= 2;
      i.len -= 2;
    }
  }
  //
  return param.array;
}

这似乎有点多余,但它提供了两个关键优势。首先是可读性和美观性。能够将 docket 的内容明显地传递到本地数组进行处理,然后将结果明显地 return 到顶部我认为对理解非常有帮助。其次,这个例子和下一个例子都使用了一种令人困惑的真值测试来过滤掉重复值检测中的误报。这个例子虽然没有太多。它可以很容易地被重写,以使用一个紧凑的、没有废话的 for 循环来比较 param.arrayparam.entry 中的每个元素。

主要问题:示例 2

docket.poke( e.key ); 是冗余较少且更理想的方法。这是我的代码。

Array.prototype.poke = function( a ) {
  var bool = {  },  entry = a,  i = {  };
  //
  this.push( entry );
  i.len = this.length;
  i.end = i.len - 1;
  //
  for ( i.cur = 0; i.cur < i.len; i.cur++ ) {
    bool.match = this[ i.cur ] == this[ i.end ];
    bool.nSelf = !( i.cur == i.end );
    //
    if ( bool.match && bool.nSelf ) {
      this.splice( i.end, 1 );
      this.splice( i.cur, 1 );
      //
      i.end -= 2;
      i.len -= 2;
    }
  }
}

如您所见,这消除了调用中的冗余,但牺牲了方法的一些可读性,更重要的是牺牲了使用我上面提到的简单比较真正精简代码的机会。

所以现在我想知道是否有一些我错过的不太明显的方法可以让我将数组的全部内容传递给局部变量而不必首先将它们作为参数传递有自己的方法。

有什么想法吗?

如果要将数组作为参数传递,则没有理由在原型上定义方法。一个简单的函数就可以了。

您的代码的第二个版本确实具有优势,您可以将方法应用于给定数组,而不是将数组传递给函数。

如果满足以下条件,则可以简化代码:

  • 您只能在确定元素尚未出现在数组
  • 后添加元素
  • 你会使用 indexOf:

Array.prototype.toggle = function(value) {
    var index = this.indexOf(value);
    if (index > -1) {
        this.splice(index, 1);
    } else {
        this.push(value);
    }
}

var a = [4,2,5,8];
a.toggle(2);
console.log(a.join());
a.toggle(2);
console.log(a.join());

注意:我个人认为 toggle 这个名字比 poke 更能说明问题。

还要考虑 Set 的强大功能:它将在常数时间内找到一个现有成员(而数组实现需要线性时间),并且还能够在常数时间内将其删除。因此,如果您愿意为此使用数组以外的其他东西,请选择 Set

Set.prototype.toggle = function(value) {
    if (!this.delete(value)) this.add(value);
}

var a = new Set([4,2,5,8]);
a.toggle(2);
console.log([...a].join());
a.toggle(2);
console.log([...a].join());