Jak mogę wygenerować unikalne liczby losowe od 1 do 100 za pomocą JavaScript?
Jak mogę wygenerować unikalne liczby losowe od 1 do 100 za pomocą JavaScript?
Odpowiedzi:
Na przykład: Aby wygenerować 8 unikalnych liczb losowych i zapisać je w tablicy, możesz po prostu zrobić to:
var arr = [];
while(arr.length < 8){
var r = Math.floor(Math.random() * 100) + 1;
if(arr.indexOf(r) === -1) arr.push(r);
}
console.log(arr);
Returns a random number between 0 (inclusive) and 1 (exclusive)
. Jeśli the Math.random()
przypadkowo zwróci 0, Math.ceil(0)
to również wynosi 0, chociaż szansa jest mała.
randlines file | head -10
.
Generować permutację 100 liczb, a następnie wybierz kolejno.
Użyj algorytmu tasowania Knutha (inaczej tasowania Fishera-Yatesa) .
JavaScript:
function fisherYates ( myArray,stop_count ) {
var i = myArray.length;
if ( i == 0 ) return false;
int c = 0;
while ( --i ) {
var j = Math.floor( Math.random() * ( i + 1 ) );
var tempi = myArray[i];
var tempj = myArray[j];
myArray[i] = tempj;
myArray[j] = tempi;
// Edited thanks to Frerich Raabe
c++;
if(c == stop_count)return;
}
}
EDYTOWAĆ :
Ulepszony kod:
function fisherYates(myArray,nb_picks)
{
for (i = myArray.length-1; i > 1 ; i--)
{
var r = Math.floor(Math.random()*i);
var t = myArray[i];
myArray[i] = myArray[r];
myArray[r] = t;
}
return myArray.slice(0,nb_picks);
}
Potencjalny problem:
Załóżmy, że mamy tablicę 100 liczb {np. [1, 2, 3 ... 100]} i przestajemy zmieniać po 8 zamianach; wtedy przez większość czasów tablica będzie wyglądać następująco: {1, 2, 3, 76, 6, 7, 8, ... liczby tutaj zostaną przetasowane ... 10}.
Ponieważ każda liczba zostanie zamieniona z prawdopodobieństwem 1/100, więc prawdopodobieństwo. zamiany pierwszych 8 liczb to 8/100, podczas gdy prawd. zamiany innych 92 to 92/100.
Ale jeśli uruchomimy algorytm dla pełnej tablicy, jesteśmy pewni (prawie) każdy wpis zostanie zamieniony.
W przeciwnym razie stajemy przed pytaniem: które 8 liczb wybrać?
Nowoczesne rozwiązanie JS wykorzystujące Set (i średni przypadek O (n))
const nums = new Set();
while(nums.size !== 8) {
nums.add(Math.floor(Math.random() * 100) + 1);
}
console.log([...nums]);
Math.floor(Math.random()*100) + 1
Set
w JS! Jednak czy to rozwiązanie nie powodowałoby niepotrzebnego generowania liczb, dopóki nie spełni się wymogu unikalności, szczególnie w ostatnich iteracjach, gdyby 8 było bliższe 100? Dlatego myślę, że wolę również elegancką odpowiedź sort
poniżej.
Powyższe techniki są dobre, jeśli chcesz uniknąć biblioteki, ale w zależności od tego, czy nie masz nic przeciwko bibliotece, sugerowałbym sprawdzenie Szansa na generowanie losowych rzeczy w JavaScript.
W szczególności, aby rozwiązać swoje pytanie, korzystanie z Chance jest tak proste, jak:
// One line!
var uniques = chance.unique(chance.natural, 8, {min: 1, max: 100});
// Print it out to the document for this snippet so we can see it in action
document.write(JSON.stringify(uniques));
<script src="http://chancejs.com/chance.min.js"></script>
Zastrzeżenie, jako autor Chance jestem nieco stronniczy;)
var codes = chance.unique(chance.string, 8)
Jeśli potrzebujesz kodów pobranych z określonej puli znaków, możesz to określić w ten sposób: chance.unique(chance.string, 8, {pool: "abcd1234"})
gdzie abcd1234 może być dowolnymi znakami, które chcesz w puli. Zobacz chancejs.com/#string
chance.string({ length: 8 })
i jeśli chcesz, aby w tym ciągu pojawiały się tylko określone znaki, chance.string({ pool: 'abcd1234', length: 8 })
co zwróci losowy ciąg 8 znaków ze znaków abcd1234, na przykład „2c2c44bc” lub „331141cc”
Aby uniknąć długich i zawodnych przetasowań, zrobiłbym następujące rzeczy ...
Voila - bez powtarzających się liczb.
Jeśli ktoś jest zainteresowany, mogę wysłać później jakiś rzeczywisty kod.
Edycja: Prawdopodobnie to moja passa konkurencyjna, ale widząc post @Alsciende, nie mogłem się powstrzymać przed wysłaniem obiecanego kodu.
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN">
<html>
<head>
<title>8 unique random number between 1 and 100</title>
<script type="text/javascript" language="Javascript">
function pick(n, min, max){
var values = [], i = max;
while(i >= min) values.push(i--);
var results = [];
var maxIndex = max;
for(i=1; i <= n; i++){
maxIndex--;
var index = Math.floor(maxIndex * Math.random());
results.push(values[index]);
values[index] = values[maxIndex];
}
return results;
}
function go(){
var running = true;
do{
if(!confirm(pick(8, 1, 100).sort(function(a,b){return a - b;}))){
running = false;
}
}while(running)
}
</script>
</head>
<body>
<h1>8 unique random number between 1 and 100</h1>
<p><button onclick="go()">Click me</button> to start generating numbers.</p>
<p>When the numbers appear, click OK to generate another set, or Cancel to stop.</p>
</body>
Innym podejściem jest wygenerowanie tablicy zawierającej 100 elementów z rosnącymi liczbami i losowe sortowanie. Prowadzi to właściwie do naprawdę krótkiego i (moim zdaniem) prostego fragmentu.
const numbers = Array(100).fill().map((_, index) => index + 1);
numbers.sort(() => Math.random() - 0.5);
console.log(numbers.slice(0, 8));
sort
jest dobrze zaimplementowany, co na pewno jest).
Zrobiłbym to:
function randomInt(min, max) {
return Math.round(min + Math.random()*(max-min));
}
var index = {}, numbers = [];
for (var i=0; i<8; ++i) {
var number;
do {
number = randomInt(1, 100);
} while (index.hasOwnProperty("_"+number));
index["_"+number] = true;
numbers.push(number);
}
delete index;
Jest to bardzo ogólna funkcja, którą napisałem, aby generować losowe unikalne / nieunikalne liczby całkowite dla tablicy. Załóżmy, że ostatni parametr jest prawdziwy w tym scenariuszu dla tej odpowiedzi.
/* Creates an array of random integers between the range specified
len = length of the array you want to generate
min = min value you require
max = max value you require
unique = whether you want unique or not (assume 'true' for this answer)
*/
function _arrayRandom(len, min, max, unique) {
var len = (len) ? len : 10,
min = (min !== undefined) ? min : 1,
max = (max !== undefined) ? max : 100,
unique = (unique) ? unique : false,
toReturn = [], tempObj = {}, i = 0;
if(unique === true) {
for(; i < len; i++) {
var randomInt = Math.floor(Math.random() * ((max - min) + min));
if(tempObj['key_'+ randomInt] === undefined) {
tempObj['key_'+ randomInt] = randomInt;
toReturn.push(randomInt);
} else {
i--;
}
}
} else {
for(; i < len; i++) {
toReturn.push(Math.floor(Math.random() * ((max - min) + min)));
}
}
return toReturn;
}
Tutaj `` tempObj '' jest bardzo użytecznym obiektem, ponieważ każda wygenerowana liczba losowa będzie bezpośrednio sprawdzać w tym tempObj, jeśli ten klucz już istnieje, jeśli nie, to zmniejszamy i o jeden, ponieważ potrzebujemy 1 dodatkowego uruchomienia, ponieważ bieżąca liczba losowa już istnieje .
W twoim przypadku wykonaj następujące czynności
_arrayRandom(8, 1, 100, true);
To wszystko.
min = (min) ? min : 1,
zawsze zwraca 1. (więc 0 nigdy nie zostanie wybrane)
Tasowanie liczb od 1 do 100 to właściwa podstawowa strategia, ale jeśli potrzebujesz tylko 8 tasowanych liczb, nie ma potrzeby tasowania wszystkich 100 liczb.
Nie znam za dobrze Javascript, ale uważam, że łatwo jest szybko utworzyć tablicę 100 wartości null. Następnie przez 8 rund zamieniasz n-ty element tablicy (n zaczynając od 0) na losowo wybrany element z przedziału od n + 1 do 99. Oczywiście wszelkie elementy, które nie zostały jeszcze wypełnione, oznaczają, że element byłby naprawdę oryginalny indeks plus 1, więc jest to trywialne do uwzględnienia. Kiedy skończysz z 8 rundami, pierwszych 8 elementów tablicy będzie miało 8 tasowanych liczb.
Ten sam algorytm permutacji co w The Machine Charmer, ale z prototypową implementacją. Lepiej nadaje się do dużej liczby kilofów. Używa przydziału destrukturyzacji js 1.7, jeśli jest dostępny.
// swaps elements at index i and j in array this
// swapping is easy on js 1.7 (feature detection)
Array.prototype.swap = (function () {
var i=0, j=1;
try { [i,j]=[j,i]; }
catch (e) {}
if(i) {
return function(i,j) {
[this[i],this[j]] = [this[j],this[i]];
return this;
}
} else {
return function(i,j) {
var temp = this[i];
this[i] = this[j];
this[j] = temp;
return this;
}
}
})();
// shuffles array this
Array.prototype.shuffle = function() {
for(var i=this.length; i>1; i--) {
this.swap(i-1, Math.floor(i*Math.random()));
}
return this;
}
// returns n unique random numbers between min and max
function pick(n, min, max) {
var a = [], i = max;
while(i >= min) a.push(i--);
return a.shuffle().slice(0,n);
}
pick(8,1,100);
Edycja: inna propozycja, lepiej dopasowana do małej liczby typów, oparta na odpowiedzi Belugaboba. Aby zagwarantować unikalność, usuwamy wybrane liczby z tablicy.
// removes n random elements from array this
// and returns them
Array.prototype.pick = function(n) {
if(!n || !this.length) return [];
var i = Math.floor(this.length*Math.random());
return this.splice(i,1).concat(this.pick(n-1));
}
// returns n unique random numbers between min and max
function pick(n, min, max) {
var a = [], i = max;
while(i >= min) a.push(i--);
return a.pick(n);
}
pick(8,1,100);
dla tablic z takimi dziurami, [,2,,4,,6,7,,]
ponieważ moim problemem było wypełnienie tych dziur. Więc zmodyfikowałem go zgodnie z moimi potrzebami :)
poniższe zmodyfikowane rozwiązanie zadziałało u mnie :)
var arr = [,2,,4,,6,7,,]; //example
while(arr.length < 9){
var randomnumber=Math.floor(Math.random()*9+1);
var found=false;
for(var i=0;i<arr.length;i++){
if(arr[i]==randomnumber){found=true;break;}
}
if(!found)
for(k=0;k<9;k++)
{if(!arr[k]) //if it's empty !!MODIFICATION
{arr[k]=randomnumber; break;}}
}
alert(arr); //outputs on the screen
Najlepszą wcześniejszą odpowiedzią jest odpowiedź wg sje397
. Otrzymasz jak najlepsze liczby losowe, tak szybko, jak to możliwe.
Moje rozwiązanie jest bardzo podobne do jego rozwiązania. Czasami jednak chcesz losowe liczby w losowej kolejności i dlatego zdecydowałem się wysłać odpowiedź. Ponadto zapewniam ogólną funkcję.
function selectKOutOfN(k, n) {
if (k>n) throw "k>n";
var selection = [];
var sorted = [];
for (var i = 0; i < k; i++) {
var rand = Math.floor(Math.random()*(n - i));
for (var j = 0; j < i; j++) {
if (sorted[j]<=rand)
rand++;
else
break;
}
selection.push(rand);
sorted.splice(j, 0, rand);
}
return selection;
}
alert(selectKOutOfN(8, 100));
Oto moja wersja ES6, którą zebrałem razem. Jestem pewien, że może być trochę bardziej skonsolidowany.
function randomArray(i, min, max) {
min = Math.ceil(min);
max = Math.floor(max);
let arr = Array.from({length: i}, () => Math.floor(Math.random()* (max - min)) + min);
return arr.sort();
}
let uniqueItems = [...new Set(randomArray(8, 0, 100))]
console.log(uniqueItems);
A co powiesz na użycie właściwości obiektu jako tablicy skrótów ? W ten sposób najlepszym scenariuszem jest losowanie tylko 8 razy. Byłoby to skuteczne tylko wtedy, gdy chcesz mieć niewielką część zakresu liczb. Zajmuje również znacznie mniej pamięci niż Fisher-Yates, ponieważ nie musisz przydzielać miejsca na tablicę.
var ht={}, i=rands=8;
while ( i>0 || keys(ht).length<rands) ht[Math.ceil(Math.random()*100)]=i--;
alert(keys(ht));
Potem dowiedziałem się, że Object.keys (obj) jest funkcją ECMAScript 5, więc powyższe jest obecnie praktycznie bezużyteczne w sieciach internetowych. Nie bój się, ponieważ dostosowałem go do ECMAScript 3, dodając taką funkcję klawiszy.
if (typeof keys == "undefined")
{
var keys = function(obj)
{
props=[];
for (k in ht) if (ht.hasOwnProperty(k)) props.push(k);
return props;
}
}
jeśli potrzebujesz więcej unikatowości, musisz wygenerować tablicę (1..100).
var arr=[];
function generateRandoms(){
for(var i=1;i<=100;i++) arr.push(i);
}
function extractUniqueRandom()
{
if (arr.length==0) generateRandoms();
var randIndex=Math.floor(arr.length*Math.random());
var result=arr[randIndex];
arr.splice(randIndex,1);
return result;
}
function extractUniqueRandomArray(n)
{
var resultArr=[];
for(var i=0;i<n;i++) resultArr.push(extractUniqueRandom());
return resultArr;
}
powyższy kod jest szybszy:
extractUniqueRandomArray (50) => [2, 79, 38, 59, 63, 42, 52, 22, 78, 50, 39, 77, 1, 88, 40, 23, 48, 84, 91, 49, 4, 54, 93, 36, 100, 82, 62, 41, 89, 12, 24, 31, 86, 92, 64, 75, 70, 61, 67, 98, 76, 80, 56, 90, 83, 44, 43, 47, 7, 53]
Dodanie kolejnej lepszej wersji tego samego kodu (zaakceptowana odpowiedź) z funkcją indexOf w JavaScript 1.6. Nie ma potrzeby przechodzenia przez całą tablicę za każdym razem, gdy sprawdzasz duplikat.
var arr = []
while(arr.length < 8){
var randomnumber=Math.ceil(Math.random()*100)
var found=false;
if(arr.indexOf(randomnumber) > -1){found=true;}
if(!found)arr[arr.length]=randomnumber;
}
Starsza wersja Javascript może nadal korzystać z wersji u góry
PS: Próbowałem zasugerować aktualizację wiki, ale została odrzucona. Nadal uważam, że może to być przydatne dla innych.
To jest moje osobiste rozwiązanie:
<script>
var i, k;
var numbers = new Array();
k = Math.floor((Math.random()*8));
numbers[0]=k;
for (var j=1;j<8;j++){
k = Math.floor((Math.random()*8));
i=0;
while (i < numbers.length){
if (numbers[i] == k){
k = Math.floor((Math.random()*8));
i=0;
}else {i++;}
}
numbers[j]=k;
}
for (var j=0;j<8;j++){
alert (numbers[j]);
}
</script>
Losowo generuje 8 unikalnych wartości tablicowych (od 0 do 7), a następnie wyświetla je za pomocą pola ostrzegawczego.
function getUniqueRandomNos() {
var indexedArrayOfRandomNo = [];
for (var i = 0; i < 100; i++) {
var randNo = Math.random();
indexedArrayOfRandomNo.push([i, randNo]);
}
indexedArrayOfRandomNo.sort(function (arr1, arr2) {
return arr1[1] - arr2[1]
});
var uniqueRandNoArray = [];
for (i = 0; i < 8; i++) {
uniqueRandNoArray.push(indexedArrayOfRandomNo[i][0]);
}
return uniqueRandNoArray;
}
Myślę, że ta metoda różni się od metod podanych w większości odpowiedzi, więc pomyślałem, że mógłbym tu dodać odpowiedź (chociaż pytanie zadano 4 lata temu).
Generujemy 100 losowych liczb i oznaczamy każdą z nich liczbami od 1 do 100. Następnie sortujemy te otagowane liczby losowe, a tagi są losowo tasowane. Alternatywnie, w razie potrzeby w tym pytaniu, można by pozbyć się po prostu znalezienia 8 pierwszych oznaczonych liczb losowych. Znalezienie 8 najlepszych elementów jest tańsze niż sortowanie całej tablicy.
Należy tutaj zauważyć, że algorytm sortowania wpływa na ten algorytm. Jeśli zastosowany algorytm sortowania jest stabilny, istnieje niewielkie odchylenie na korzyść mniejszych liczb. Idealnie byłoby, gdyby algorytm sortowania był niestabilny i nawet nie był nastawiony na stabilność (lub niestabilność), aby uzyskać odpowiedź z idealnie jednorodnym rozkładem prawdopodobieństwa.
Może to obsłużyć generowanie do 20 cyfr UNIKALNEJ liczby losowej
JS
var generatedNumbers = [];
function generateRandomNumber(precision) { // input --> number precision in integer
if (precision <= 20) {
var randomNum = Math.round(Math.random().toFixed(precision) * Math.pow(10, precision));
if (generatedNumbers.indexOf(randomNum) > -1) {
if (generatedNumbers.length == Math.pow(10, precision))
return "Generated all values with this precision";
return generateRandomNumber(precision);
} else {
generatedNumbers.push(randomNum);
return randomNum;
}
} else
return "Number Precision shoould not exceed 20";
}
generateRandomNumber(1);
To rozwiązanie używa skrótu, który jest znacznie wydajniejszy O (1) niż sprawdzenie, czy rezyduje w tablicy. Ma również dodatkowe bezpieczne kontrole. Mam nadzieję, że to pomoże.
function uniqueArray(minRange, maxRange, arrayLength) {
var arrayLength = (arrayLength) ? arrayLength : 10
var minRange = (minRange !== undefined) ? minRange : 1
var maxRange = (maxRange !== undefined) ? maxRange : 100
var numberOfItemsInArray = 0
var hash = {}
var array = []
if ( arrayLength > (maxRange - minRange) ) throw new Error('Cannot generate unique array: Array length too high')
while(numberOfItemsInArray < arrayLength){
// var randomNumber = Math.floor(Math.random() * (maxRange - minRange + 1) + minRange)
// following line used for performance benefits
var randomNumber = (Math.random() * (maxRange - minRange + 1) + minRange) << 0
if (!hash[randomNumber]) {
hash[randomNumber] = true
array.push(randomNumber)
numberOfItemsInArray++
}
}
return array
}
document.write(uniqueArray(1, 100, 8))
Implementacja tego jako generatora sprawia, że praca z nim jest całkiem przyjemna. Uwaga, ta implementacja różni się od tych, które wymagają najpierw przetasowania całej tablicy wejściowej.
Ta
sample
funkcja działa leniwie, dając 1 losowy przedmiot na iterację, aż doN
przedmiotów, o które prosisz. Jest to miłe, ponieważ jeśli chcesz tylko 3 pozycje z listy 1000 , nie musisz najpierw dotykać wszystkich 1000 pozycji.
// sample :: Integer -> [a] -> [a]
const sample = n => function* (xs) {
let ys = xs.slice(0);
let len = xs.length;
while (n > 0 && len > 0) {
let i = (Math.random() * len) >> 0;
yield ys.splice(i,1)[0];
n--; len--;
}
}
// example inputs
let items = ['a', 'b', 'c', 'd', 'e', 'f', 'g'];
let numbers = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9];
// get 3 random items
for (let i of sample(3) (items))
console.log(i); // f g c
// partial application
const lotto = sample(3);
for (let i of lotto(numbers))
console.log(i); // 3 8 7
// shuffle an array
const shuffle = xs => Array.from(sample (Infinity) (xs))
console.log(shuffle(items)) // [b c g f d e a]
Zdecydowałem się zaimplementować sample
w sposób, który nie powoduje mutacji tablicy wejściowej, ale można łatwo argumentować, że implementacja mutująca jest korzystna.
Na przykład shuffle
funkcja może chcieć zmodyfikować oryginalną tablicę wejściową. Lub możesz chcieć próbkować z tego samego wejścia w różnych momentach, aktualizując wejście za każdym razem.
// sample :: Integer -> [a] -> [a]
const sample = n => function* (xs) {
let len = xs.length;
while (n > 0 && len > 0) {
let i = (Math.random() * len) >> 0;
yield xs.splice(i,1)[0];
n--; len--;
}
}
// deal :: [Card] -> [Card]
const deal = xs => Array.from(sample (2) (xs));
// setup a deck of cards (13 in this case)
// cards :: [Card]
let cards = 'A234567890JQK'.split('');
// deal 6 players 2 cards each
// players :: [[Card]]
let players = Array.from(Array(6), $=> deal(cards))
console.log(players);
// [K, J], [6, 0], [2, 8], [Q, 7], [5, 4], [9, A]
// `cards` has been mutated. only 1 card remains in the deck
console.log(cards);
// [3]
sample
nie jest już czystą funkcją z powodu mutacji wejścia tablicy, ale w pewnych okolicznościach (pokazanych powyżej) może mieć więcej sensu.
Innym powodem, dla którego wybrałem generator zamiast funkcji, która po prostu zwraca tablicę, jest to, że możesz chcieć kontynuować próbkowanie do określonego warunku.
Być może chcę pierwszą liczbę pierwszą z listy 1 000 000 liczb losowych.
Ponieważ pracujemy z generatorem, to zadanie jest banalne
const randomPrimeNumber = listOfNumbers => {
for (let x of sample(Infinity) (listOfNumbers)) {
if (isPrime(x))
return x;
}
return NaN;
}
Spowoduje to ciągłe próbkowanie 1 losowej liczby naraz x
, sprawdź, czy jest to liczba pierwsza, a następnie zwróci, x
jeśli tak jest. Jeśli lista liczb zostanie wyczerpana przed znalezieniem liczby pierwszej, NaN
zwracana jest wartość.
Uwaga:
Ta odpowiedź została pierwotnie udostępniona na inne pytanie, które zostało zamknięte jako duplikat tego. Ponieważ bardzo różni się od innych przedstawionych tutaj rozwiązań, postanowiłem się nim również podzielić
getRandom (min, max) {
return Math.floor(Math.random() * (max - min)) + min
}
getNRandom (min, max, n) {
const numbers = []
if (min > max) {
return new Error('Max is gt min')
}
if (min === max) {
return [min]
}
if ((max - min) >= n) {
while (numbers.length < n) {
let rand = this.getRandom(min, max + 1)
if (numbers.indexOf(rand) === -1) {
numbers.push(rand)
}
}
}
if ((max - min) < n) {
for (let i = min; i <= max; i++) {
numbers.push(i)
}
}
return numbers
}
Korzystanie z a Set
to najszybsza opcja. Oto ogólna funkcja do uzyskiwania unikalnej liczby losowej, która używa generatora wywołań zwrotnych. Teraz jest szybki i wielokrotnego użytku .
// Get a unique 'anything'
let unique = new Set()
function getUnique(generator) {
let number = generator()
while (!unique.add(number)) {
number = generator()
}
return number;
}
// The generator. Return anything, not just numbers.
const between_1_100 = () => 1 + Math.floor(Math.random() * 100)
// Test it
for (var i = 0; i < 8; i++) {
const aNumber = getUnique(between_1_100)
}
// Dump the 'stored numbers'
console.log(Array.from(unique))
Jest to implementacja Shuffle Fisher Yates / Durstenfeld , ale bez faktycznego tworzenia tablicy, co zmniejsza złożoność przestrzeni lub ilość potrzebnej pamięci, gdy rozmiar pobrania jest mały w porównaniu z liczbą dostępnych elementów.
Aby wybrać 8 liczb ze 100, nie jest konieczne tworzenie tablicy 100 elementów.
Zakładając, że utworzono tablicę,
rnd
) od 1 do 100 rnd
Jeśli tablica nie zostanie utworzona, można użyć mapy hashMap do zapamiętania rzeczywistych zamienionych pozycji. Kiedy druga wygenerowana liczba losowa jest równa jednej z poprzednio wygenerowanych liczb, mapa podaje bieżącą wartość w tej pozycji, a nie rzeczywistą wartość.
const getRandom_ = (start, end) => {
return Math.floor(Math.random() * (end - start + 1)) + start;
};
const getRealValue_ = (map, rnd) => {
if (map.has(rnd)) {
return getRealValue_(map, map.get(rnd));
} else {
return rnd;
}
};
const getRandomNumbers = (n, start, end) => {
const out = new Map();
while (n--) {
const rnd = getRandom_(start, end--);
out.set(getRealValue_(out, rnd), end + 1);
}
return [...out.keys()];
};
console.info(getRandomNumbers(8, 1, 100));
console.info(getRandomNumbers(8, 1, Math.pow(10, 12)));
console.info(getRandomNumbers(800000, 1, Math.pow(10, 15)));
Oto przykład losowych 5 liczb z zakresu od 0 do 100 (w tym 0 i 100) bez powielania.
let finals = [];
const count = 5; // Considering 5 numbers
const max = 100;
for(let i = 0; i < max; i++){
const rand = Math.round(Math.random() * max);
!finals.includes(rand) && finals.push(rand)
}
finals = finals.slice(0, count)
Możesz to również zrobić za pomocą jednej wkładki w ten sposób:
[...((add, set) => add(set, add))((set, add) => set.size < 8 ? add(set.add(Math.floor(Math.random()*100) + 1), add) : set, new Set())]