我有一个这样的数组:

var arr1 = ["a", "b", "c", "d"];

我如何随机化/打乱它?


当前回答

编辑:此答案不正确

参见评论和https://stackoverflow.com/a/18650169/28234.这里留作参考,因为这种想法并不罕见。


对于小型阵列,一个非常简单的方法就是:

const someArray = [1, 2, 3, 4, 5];

someArray.sort(() => Math.random() - 0.5);

它可能效率不高,但对于小型阵列来说,这很好。这里有一个例子,你可以看到它有多随机(或不随机),以及它是否适合你的用例。

const resultsEl=document.querySelector(“#results”);const buttonEl=document.querySelector(“#trigger”);常量生成器数组和随机化=()=>{常量someArray=[0,1,2,3,4,5,6,7,8,9];someArray.sort(()=>Math.random()-0.5);return someArray;};const renderResultsToDom=(结果,el)=>{el.innerHTML=results.join(“”);};buttonEl.addEventListener('click',()=>renderResultsToDom(generateArray AndRandomize(),resultsEl));<h1>随机化</h1><button id=“trigger”>生成</button><p id=“results”>0 1 2 3 4 5 6 7 8 9</p>

其他回答

使用ES6功能的现代短内联解决方案:

['a','b','c','d'].map(x => [Math.random(), x]).sort(([a], [b]) => a - b).map(([_, x]) => x);

(出于教育目的)

您可以轻松地使用地图和排序:

让unshuffled=['hello','a','t','q',1,2,3,{cats:true}]让洗牌.map(value=>({value,sort:Math.random()})).sort((a,b)=>a.sort-b.sort).map(({value})=>值)console.log(混洗)

我们将数组中的每个元素放在一个对象中,并给它一个随机排序键我们使用随机键排序我们取消映射以获取原始对象

您可以对多态数组进行排序,排序就像Math.random一样随机,这对于大多数目的来说都足够好。

由于元素是根据每次迭代都不会重新生成的一致键进行排序的,并且每次比较都来自相同的分布,因此Math.random分布中的任何非随机性都会被取消。

速度

时间复杂度为O(N log N),与快速排序相同。空间复杂度为0(N)。这不像Fischer Yates洗牌那样高效,但在我看来,代码明显更短,功能更强大。如果你有一个大数组,你当然应该使用Fischer Yates。如果您有一个包含几百个项目的小数组,您可以这样做。

$=(m)=>控制台日志(m);//----将此方法添加到Array类Array.prototype.shuffle=函数(){return this.sort(()=>.5-Math.random());};$([1,65,87,45101,33,9].shuffle());$([1,65,87,45101,33,9].shuffle());$([1,65,87,45101,33,9].shuffle());$([1,65,87,45101,33,9].shuffle());$([1,65,87,45101,33,9].shuffle());

我在考虑在控制台上粘贴oneliner。sort的所有技巧都给出了错误的结果,下面是我的实现:

 ['Bob', 'Amy', 'Joy'].map((person) => `${Math.random().toFixed(10)}${person}`).sort().map((person) => person.substr(12));

但不要在生产代码中使用它,它不是最佳的,只适用于字符串。

费希尔·耶茨在javascript中洗牌。我在这里发表这篇文章是因为与这里的其他答案相比,使用两个实用函数(swap和randInt)澄清了算法。

function swap(arr, i, j) { 
  // swaps two elements of an array in place
  var temp = arr[i];
  arr[i] = arr[j];
  arr[j] = temp;
}
function randInt(max) { 
  // returns random integer between 0 and max-1 inclusive.
  return Math.floor(Math.random()*max);
}
function shuffle(arr) {
  // For each slot in the array (starting at the end), 
  // pick an element randomly from the unplaced elements and
  // place it in the slot, exchanging places with the 
  // element in the slot. 
  for(var slot = arr.length - 1; slot > 0; slot--){
    var element = randInt(slot+1);
    swap(arr, element, slot);
  }
}