【问题标题】:Fast way to check if a javascript array is binary (contains only 0 and 1)检查 javascript 数组是否为二进制的快速方法(仅包含 0 和 1)
【发布时间】:2018-09-19 11:08:50
【问题描述】:

有什么方法可以快速确定一个数组是否仅由 0 和 1 组成?

我对布尔解决方案有点熟悉,但不知道如何实现它。为了实现,您必须将值分配给布尔值

true = 0 

false = 1 

但是如果给你一个这样的数组,你将如何实现呢

array = [1,1,1,1,0,0,0,0]

isArrayBool (){ 

}

【问题讨论】:

  • array.every(v => v === 0 || v === 1)
  • 注意 ... true=1false=0 更符合逻辑... 特别是因为 +true === 1+false === 0
  • 更快的方法是使用for 循环。
  • StackOverflow 不是免费的编码服务。所以希望你try to solve your own problem first。请更新您的问题以在minimal reproducible example 中显示您已经尝试过的内容。如需更多信息,请参阅How to Ask,并拨打tour :)
  • @ibrahimmahrir - 我明白你为什么说 for 循环更快 - 因为 Chrome 原生数组方法(一些、每个等)慢得可怜

标签: javascript arrays binary boolean


【解决方案1】:

非常非常幼稚的解决方案:

function isArrayBool(array) {
    for (var i of array) {
         if (i !== 0 && i !== 1) return false;
    }
    return true;
}

console.log(isArrayBool([1,0,0,0,1]));   // true
console.log(isArrayBool([1]));           // true
console.log(isArrayBool([2,3,0]));       // false

【讨论】:

  • 它是“in”而不是“of”
  • @ibrahimmahrir 我的代码运行顺利,我认为选择i 作为对象而不是作为索引让你感到困惑。
  • 那么,为什么isArrayBool([0,1,1,1,1]) 会产生 false - 我认为您在 of 和 in 之间缺乏知识让您感到困惑 @DanieleCappuccio
  • @DanieleCappuccio 在你的for 下添加一个console.log(i) 看看它说了什么。
  • 你们是对的,我对此非常确定。编辑我的答案:)
【解决方案2】:

所以我把几个函数放在jsperf中一起测试。目前我发现最快的是下面那个(比for of版本快很多):

function isBoolFor(arr) {
  for(var i=arr.length-1; i>=0; --i){
    if(arr[i] !== 0 && arr[i] !== 1) return false
  }
  return true
}

比较是here


编辑:我玩了另一个版本,结果更快:

function isBoolFor(arr) {
  for(var i=0; arr[i] === 0 || arr[i] === 1; i++){}
  return i === arr.length
}

这里的关键是,因为您要检查的大部分数组都包含 0 和 1,所以您可以通过使用 || 而不是 && 否定检查来避免每次迭代都进行两次布尔检查。这只是一个细微的改进,在实用性上可以说不比上述改进。


更新:所以所有 for 和 while 变体之间的差异太微妙了,无法宣布总冠军。所以在那种情况下,我会追求可读性。如果你想要二进制使用类型数组!


最终更新:

我很好奇,想找到一个更快的版本,如果已知数组只有数字,就可以做到。如果数组只包含数字,那么您可以使用按位运算符检查任何一个有问题的值。例如:

function isBoolFor(arr) {
  const test = ~0x01
  for(var i=arr.length-1; i>=0; --i){
    if(test & arr[i]){ return false }
  }
  return true
}

【讨论】:

    【解决方案3】:

    https://jsperf.com/bool-array-test-2/1

    正如我们在这里看到的,最快的方法可以在这里看到...使用简单的 for 循环,正如用户 Jaromanda 在评论中所建议的那样。这个 for 循环在速度方面将其他解决方案从水中吹走。

     var someArray = [1,0,1,1,1,1,0,0,1,0,1,0,0,1,0,1,0,1,1,1,1,0,1,1,0,1,0]; 
    
     function simpleForLoop(array){
       var numArgs = someArray.length;
       for(var loop = 0; loop < numArgs; loop++){
        var arg = someArray[loop];
        if(arg  !== 0 && arg !== 1){ return false; }
       }
       return true;
      }
    
      var isbool = simpleForLoop(someArray);
    

    【讨论】:

    • 是的,很尴尬。我删除了我的另一个答案,因为虽然它比其他答案更好,但它远远落后于一个简单的 for 循环。我一直在 PHP 和 JS 中使用它们,但老实说,我认为 .every() 函数会击败 for (因为当我的函数返回第一个 false 时它会停止,所以它不会命中每个数组 val - for 也可以,但认为every() 会击败它。不!)...但我错了。 for 循环再次获胜!
    • 是的,认为内置 javascript 的性能接近 c 速度是可以原谅的。但请检查,&amp;&amp; 我想你想要||
    • 好吧,我们说如果数组值不是 0 并且不是 1,那么它不是布尔值并返回 false。否则,返回真。如果我们使用 ||然后它说如果它是 0 或它不是 1,则返回 false ......这意味着如果它是 1,它将返回 false 因为它说如果它不是 1 或 0 并且它不是 0 则返回......所以我们使用 && 表示“与”。
    • 是的,这不应该在 for() 中
    • 感谢您的坚持。我认为这是值得的。
    猜你喜欢
    • 2023-02-10
    • 1970-01-01
    • 1970-01-01
    • 2020-10-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-01-14
    • 2018-08-04
    相关资源
    最近更新 更多