【问题标题】:Is there a way to randomize an array to a certain length in JS?有没有办法在JS中将数组随机化到一定长度?
【发布时间】:2021-08-05 23:05:54
【问题描述】:

假设我有一个数组:

array1 = [1, 2, 3, 4, 5, ........, 50]

我想将该数组随机化为一个具有长度限制的新数组。

例如,如果我想从 array1 中得到一个只有 5 个数字长的随机数组,我可以得到:

var arrayLength = 5

randomizedArray = [6, 20, 45, 2, 13]

有没有办法用 Math.random 做到这一点?

【问题讨论】:

  • 可以迭代数组5次,随机push一个索引

标签: javascript arrays random


【解决方案1】:

您可以映射数组并将每个项目设置为Math.random() 乘以上限(四舍五入)的结果:

function generateRandomArray(length, RNGUpperBound){
  return new Array(length).fill().map(e => Math.round(Math.random() * RNGUpperBound))
}
console.log(generateRandomArray(5, 10));

【讨论】:

  • 这是完美的,但有没有办法在满足某些条件之前保持随机化?
  • @ccardinale98 您可以使用 while 循环继续生成数组,直到满足条件。
【解决方案2】:

只要范围 (0..60) 不是非常大,我就会洗牌和切片。将数组 shuffle 作为一个常用的工具是一个好主意。

// from https://stackoverflow.com/a/2450976/294949
function fyShuffle(array) {
  let currentIndex = array.length,  randomIndex;
  while (0 !== currentIndex) {
    randomIndex = Math.floor(Math.random() * currentIndex);
    currentIndex--;
    [array[currentIndex], array[randomIndex]] = [
      array[randomIndex], array[currentIndex]];
  }
  return array;
}

let range = 60;
let resultLength = 5;
let array1 = [ ...Array(range).keys() ]; // the OP array

fyShuffle(array1);
console.log(array1.slice(0, resultLength))

【讨论】:

    【解决方案3】:

    您可以迭代数组 5 次并使用 Math.random() 随机推送索引:

    let array1 = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50];
    
    let newLength = 5,
        newArray = [];
    
    for (let i = 0; i < 5; i ++) {
      newArray.push(array1[Math.floor(Math.random()  * (array1.length - 1))]);
    }
    
    console.log(newArray);

    但是,这不会避免推送两次或多次相同的项目。您可以先使用includes() 方法检查该项目是否已包含:

    let array1 = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50];
    
    let newLength = 5,
      newArray = [];
    
    for (let i = 0; i < 5; i++) {
      let randomElem = null;
      // Check if element is already in the array
      do {
        randomElem = array1[Math.floor(Math.random() * (array1.length - 1))];
      }while(newArray.includes(randomElem));
      
      newArray.push(randomElem);
    }
    
    console.log(newArray);

    【讨论】:

      【解决方案4】:

      其他人都已经讨论过执行此操作的正常方法。我只想说rando.js 非常适合这些东西。

      //if you have to use an array
      var arr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50];
      console.log(randoSequence(arr).map(a => a.value).slice(-5));
      
      //or if you prefer to be kind to yourself
      console.log(randoSequence(1, 50).slice(-5))
      &lt;script src="https://randojs.com/2.0.0.js"&gt;&lt;/script&gt;

      【讨论】:

        【解决方案5】:

        这里,代码应该添加n distinct values,而不是添加n values(如果需要的话),因为如果n接近数组的长度,则元素可能会重复。

        这是一个简单的代码sn-p,没有导入任何新的node_module。

        let array = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50];
        let newArrayLength = 10;
        let newArray = [];
        
        while (newArrayLength > 0) {
          const rndIndex = Math.floor(Math.random() * array.length);
          if (!newArray.includes(array[rndIndex])) {
          newArray.push(array[rndIndex]);
          newArrayLength--;
          }
        }
        console.log('newArray', newArray);

        【讨论】:

          【解决方案6】:

          方法一:打乱整个数组,取前N个元素

          您始终可以对整个数组进行洗牌,然后取出前 5 个元素。这会浪费时间和内存,但这仅适用于非常大的输入或性能存在问题的情况。

          使用任何common method 来打乱数组:

          function shuffle(array) {
              return array.map((value) => ({ value, sort: Math.random() }))
                  .sort((a, b) => a.sort - b.sort)
                  .map(({ value }) => value)
          }
          

          然后:

          const arrayLength = 5;
          const array1 = [1, 2, ..., 50];
          
          const shuffled = shuffle(array1);
          // take the first n elements from the shuffled array
          const sample = shuffled.slice(0, arrayLength);
          
          

          方法 2:使用库

          许多库已经实现了类似的东西 - 您正在寻找的是一个 N 个元素的随机样本。例如,试试 lodash 的 sampleSize as discussed in this answer

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 2022-01-22
            • 2021-07-19
            • 1970-01-01
            • 2021-03-30
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多