如何使用 for、for of 或 forEach 遍历 2 个数组作为参数

问题描述

我对 Javascript 有点陌生,所以我会尽力解释这一点。我在 fizz buzz 循环中使用了 vanilla JS,但我想我尝试的做法略有不同。

我已将两组数字放在 2 个单独的数组中,并通过 for 循环成功地通过计数到 20,但我没有使用数组来执行此操作。但是,我想使用作为参数传递的变量来检查值是否为真,以便可以打印适当的响应,无论是 fizz、buzz 还是 fizzbuzz。

我的 for 循环代码是:

const fizz = [3,6,9,12,15,18];
const buzz = [5,10,20];

for (let i = 1; i <= 20; i++){
    if(i % 3 === 0 && i % 5 === 0) {
        console.log(i + " fizz buzz");
    } else if(i % 3 === 0){
       console.log(i + " fizz");
    } else if(i % 5 === 0) {
    console.log(i + " buzz");
    } else {
        console.log(i);
    }
}
.as-console-wrapper {max-height: 100%!important;top:0}

正如我所说,它运行成功。

我确实使用 fizz & buzz 变量编辑了 for 循环,但没有成功。我尝试使用 indexindexOf,但我不确定如何编码。

我也使用过 for offorEach,但我也在苦苦思索如何编写这些代码

我知道这很麻烦,但我如何编写 forEach 方法如下所示:

fizz.forEach(function(value) {
     if (i === fizz.indexOf[value]) {
        console.log(value);
         i++;
     }
});

最终我对所有这些的问题是 - 我如何将这些数组作为参数传递以循环并检查它们的值是否为真?而且,哪种方法最好?

解决方法

您可以使用函数 some 测试您要迭代的数字是否在任何数组内。例如,

const fizz = [3,6,9,12,15,18];
const buzz = [5,10,20];

for(let i = 1; i <= 20; i++){
    const isFizz = fizz.some(f => f === i);
    const isBuzz = buzz.some(b => b == i);
    if(isFizz && isBuzz){
        console.log(i + " fizz buzz");
    } else if(isFizz){
        console.log(i + " fizz");
    } else if(isBuzz){
        console.log(i + " buzz");
    } else {
        console.log(i);
    }
}

*注意:整个算法的性能高于线性,因为 some() 迭代数组并在 for 循环内。另一种方法是使 isFizz = n => n%3 === 0isBuzz = n => n%5 === 0,并获得线性时间复杂度。

,

你可以这样做...

const 
  fizz = [3,18],buzz = [5,20]
  ;
fizz.concat(buzz).sort((a,b)=>a-b).forEach((v,i,{[i+1]:n})=>
  {
  if (v!=n)
    console.log(v,!fizz.includes(v) ? 'buzz': buzz.includes(v) ? 'fizz buzz': 'fizz' ) 
  })
.as-console-wrapper {max-height: 100%!important;top:0}

你介意解释一下吗?
@KENAXION

javascript 语言允许使用方法和函数的链接
所以

fizz.concat(buzz).sort((a,b)=>a-b).forEach(...)

相当于

let arr = fizz.concat(buzz) // adding fizz buzz into new array ( named arr )
arr.sort((a,b)=>a-b)
arr.forEach(...)

在这个链接中:
Array.concat(...) 返回一个新数组
女巫被 arr.sort(...) 使用并返回一个引用到同一个数组“已排序”
arr.forEach(...)

使用女巫

sort 方法使用 Arrow function expressions

arr.sort((a,b)=>a-b)

等于

arr.sort( function(a,b) { return a-b } )

Array.forEach()也使用箭头函数表达式,
他的内部函数可以接受 3 个参数:
~ 当前循环元素,
~他的索引,
~ 对原始数组的引用(在链式操作中很有用;就像这里)

此处对原始数组的引用经过转换以返回元素 i + 1 的值,通过操作 { [i + 1] : n },在名为 n 的变量中(对于 n 外)

故事:
fizz 和 buzz 的串联数组在排序时,有些元素是重复的,排序后不可避免地会互相跟随。 这里,忽略这些重复的方法是检查处理的元素是否与其下一个 if (v != n) 的元素不同。

然后 console.log 调用双三元测试

!fizz.includes(v) ? 'buzz': buzz.includes(v) ? 'fizz buzz': 'fizz'

总结如下:

if (!fizz.includes(v)      return 'buzz'
else if (buzz.includes(v)) return 'fizz buzz'
else                       return 'fizz'

文档链接:
Array.concat()Array.sort()Array.forEach()Conditional (ternary) operatorArray.includes()

如果你真的需要获取中间值

const arrs =
  { fizz : Array.from({length: 6},(_,i)=>(i+1)*3),buzz : Array.from({length: 4},i)=>(i+1)*5),zazz : [ 1,3,5,8 ]
  };

Object.values(arrs)
  .reduce((sum,arr)=>sum.concat(arr),[])
  .sort((a,b)=>a-b)
  .forEach((v,{[i-1]:p})=>
  {
  for(let n=(p??0)+1;n<v;++n) console.log(n)
  if (v!=p)
    console.log(v,Object.keys(arrs).filter((nm)=>arrs[nm].includes(v)).join(' ') ) 
  })
.as-console-wrapper {max-height: 100%!important;top:0}

布尔值:

在简单的相等测试的情况下,Array.includes()Array.some()
更快且更可取 和
一个简单的数组引用,如果比 if

的级联更快

console.time('speed test')

const 
  fizz = [3,20],txts = [ '','fizz','buzz','fizz buzz']
  ;
for (let i = 1; i <= 20; ++i ) 
  {
  let ref = fizz.includes(i) ? 1 : 0;
     ref |= buzz.includes(i) ? 2 : 0;
  console.log( i,txts[ref] )
  }

console.timeEnd('speed test')
.as-console-wrapper {max-height: 100%!important;top:0}

最后一个解决方案(4)

const arrs  =
  [ { fizz: [ 3,18] },{ buzz: [ 5,20 ] },{ zazz: [ 1,8 ] }
  ]

showArrCom(arrs) 

function showArrCom(ArrList)
  {
  const
    arrN = ArrList.map(o=>Object.entries(o).reduce((r,[k,v])=>({n:k,i:0,a:v}),{})),doLoop =_=> arrN.reduce((t,{a,i})=>t || (a[i]!=undefined),false)
    ;
  for (let indx=1; doLoop(); indx++ )
    {
    document.write( arrN.reduce((m,{n,a,i},x,t)=>
      {
      if (a[i]===indx) { m += `${n} `; t[x].i++ }
      return m
      },`${indx} `) + '<br>')
    }
  }

,

我对您要完成的任务感到有些困惑,但我想我明白了……您想检查给定的数字是否在其中一个数组中,对吗?

为此,您可以使用 .includes.indexOf

.includes 将检查数组中是否存在该值,而 .indexOf 将为您提供数组中该值的索引,如果不存在,则为 -1。>

此外,对于您进行的 .forEach 尝试。首先,您需要创建一个数组,该数组的数字范围为 1 到 20。然后,使用您已经构建的相同逻辑在创建的范围上应用 .forEach

考虑到这一点,您还可以扩展代码以添加多个数组。

const fizz = [3,20];

// create range of number from X to Y
const createRange = (FROM,TO) => [...Array(TO - FROM + 1).keys()].map(i => i + FROM);

const values = createRange(1,20);

console.log('using includes...');
values.forEach(i => {
    const isFizz = fizz.includes(i);
    const isBuzz = buzz.includes(i);
    if(isFizz && isBuzz) console.log(i + " fizz buzz");
    else if(isFizz) console.log(i + " fizz");
    else if(isBuzz) console.log(i + " buzz");
    else console.log(i);
});

console.log('using indexOf...');
values.forEach(i => {
    const isFizz = fizz.indexOf(i) !== -1;
    const isBuzz = buzz.indexOf(i) !== -1;
    if(isFizz && isBuzz) console.log(i + " fizz buzz");
    else if(isFizz) console.log(i + " fizz");
    else if(isBuzz) console.log(i + " buzz");
    else console.log(i);
});


const arrs = {
  fizz: [3,buzz: [5,zazz: [1,8],}

console.log('with multiple input arrays');
values.forEach(i => {
  const output = [i];
  Object.keys(arrs).forEach(key => {
    if (arrs[key].includes(i)) output.push(key);
  });
  
  console.log(output.join(' '));
});

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...