Go Down

Topic: New random number loop (Read 470 times) previous topic - next topic

Weller

Hi,

Im trying to create an array of 5 different numbers between 1 and 20.

However i need to make sure all the numbers are unique.  Obviously if I request a new random number each time then theres a good chance there will be duplicates.  How do I code this?

At the moment I have:

Code: [Select]

for(int x = 0; x < 5; x++) {
  int i = random(1,21);
  myArray[x] = i;
}



Thanks :)

robtillaart


one solution is put all numbers in an array, scramble them and take the first 5.

Code: [Select]

  int numbers[] = { 0,1,2,3,4,5,6,7,8,9,10,11,12,13 };
  int count = 13;


void setup()
{
  Serial.begin(9600);
 
  scrambleArray(numbers, count);
  for (int i=0; i<count; i++)
  {
    Serial.println(numbers[i]);
  }
  Serial.println("----");
}

void loop()
{}

void scrambleArray(int * array, int size)
{
  int last = 0;
  int temp = array[last];
  for (int i=0; i<size; i++)
  {
    int index = random(size);
    array[last] = array[index];
    last = index;
  }
  array[last] = temp;
}


Another solution is to remember the values you got "thrown", if one is already in the list rethrow the dice ...

Rob Tillaart

Nederlandse sectie - http://arduino.cc/forum/index.php/board,77.0.html -
(Please do not PM for private consultancy)

michinyon

I'd be a bit worried that you put 14 numbers in that array and then sorted 13 of them.

PeterH


However i need to make sure all the numbers are unique.  Obviously if I request a new random number each time then theres a good chance there will be duplicates.  How do I code this?


One method is for each element in the array, keep generating numbers until you find one that is not already present in the array.

I'm not going to code it for you, but you would need:

  • A for loop to process each element in the array.

  • A while loop inside it to process the current element repeatedly until a unique random number had been found

  • A for loop inside that to compare the currently proposed random number against all the preceding elements in the array


I only provide help via the forum - please do not contact me for private consultancy.

robtillaart

Quote
I'd be a bit worried that you put 14 numbers in that array and then sorted 13 of them.

At least someone notices ;)

It shows a degree of freedom the algorithm has, you can randomize only first part of the array ;)


Drawback of algorithms that need to check if there a number is already chosen like the one I proposed myself (last line of prev post) that they can take a large amount of time, especially when the list of numbers to choose from and the numbers needed are in the same order of magnitude.

There is also the algorithm (Dijkstra/Knuth?) that is linear with the amount of numbers. This algorithm generates one number per iteration but it needs an array with all numbers to be chosen from. It works as follows:

take an array of 20 elements.
take one element x=random(20)
remove element x from the array by moving the last element of the array to x
make the array 1 element smaller; //ignore last element
take one element x=random(19)
remove element x from the array by moving the last element of the array to x
make the array 1 element smaller; //ignore last element
etc..

(snippet)
Code: [Select]
for (int i = 0; i < 5; i++)
{
  int x = random(20-i);
  Serial.println(array[x]);
  array[x] = array[20-i];
}


Drawback of this algorithm is that it needs the array of numbers to choose from.
Rob Tillaart

Nederlandse sectie - http://arduino.cc/forum/index.php/board,77.0.html -
(Please do not PM for private consultancy)

Go Up