7

I would like to make a for loop that loops through the numbers 0-8 in a random order. Note that every number can only be visited once.

How can I achieve this?

BBB
  • 615
  • 3
  • 12
  • 26
  • 3
    [This SO question](http://stackoverflow.com/questions/254844/random-array-using-linq-and-c-sharp) is what you are looking for – Zbigniew Nov 19 '12 at 16:23
  • I have tried making a list of the integers 0-8 and taking one at random and removing it afterwards. But in my program I'm using a recursive method where such a solution isn't practical – BBB Nov 19 '12 at 16:24
  • @BrunoCarvalhal Perhaps you should post a sample of how you've designed your recursion as that appears to be a significant element to your question/answer. – Chris Sinclair Nov 19 '12 at 16:26
  • @des, that question discusses a random sequence (with repeats), not a random permutation – Dan Bryant Nov 19 '12 at 16:26
  • @DanBryant It generates a random number listing of `1-100` with no repeats. – Chris Sinclair Nov 19 '12 at 16:28
  • @DanBryant I might be wrong, but link which I've provided shows how to create sequence of random numbers, later on this sequence could be used in loop. Am I not right? – Zbigniew Nov 19 '12 at 16:28
  • @des, ah, sorry, you're correct; it's using randomization to impact the ordering for an effective shuffle. – Dan Bryant Nov 19 '12 at 16:29
  • If you really care about randomness and want a lack of bias, check this out http://en.wikipedia.org/wiki/Knuth_shuffle – Jodrell Nov 19 '12 at 16:38

4 Answers4

23
Random r = new Random();
foreach (int i in Enumerable.Range(0, 9).OrderBy(x => r.Next()))
{
    Console.WriteLine(i);
}
L.B
  • 114,136
  • 19
  • 178
  • 224
  • What I was about to type and also similar to what is linked here http://stackoverflow.com/a/254861/659190 – Jodrell Nov 19 '12 at 16:31
  • 1
    Perfect! Exactly what I was looking for. I got too focussed on a for loop while I should have used this foreach loop. – BBB Nov 19 '12 at 16:33
  • Great answer. If it helps other noobs like me, IEnumerable.OrderBy is an extension method in the System.Linq namespace. – geo May 04 '17 at 04:32
6
  1. Generate an array of the indices 0 to 8
  2. Shuffle the array
  3. Iterate over the array using the index at that position
Phil H
  • 19,928
  • 7
  • 68
  • 105
  • Why in the world you took the 8 out? – LMB Nov 19 '12 at 16:24
  • Probably just misread figuring it was an array/list of length `8` so you'd only want element indices `0` to `7`. – Chris Sinclair Nov 19 '12 at 16:27
  • 1
    This answer isn't helpful if you don't explain how to shuffle the contents. – Kevin Kalitowski Nov 19 '12 at 16:27
  • I disagree - an array shuffle is easy to implement, and this is the approach I would have suggested. (+1 despite the typo) – Hugh Jones Nov 19 '12 at 16:30
  • @KevinKalitowski: There are many ways to shuffle, and shuffling isn't the subject of the question. The point was to separate the generation of the index list from the iteration over the indices. – Phil H Nov 19 '12 at 16:38
0

One possibility:

var numbers = Enumerable.Range(0, 9).ToList();
var rnd =  new Random();
for (; numbers.Count != 0; )
{
    var currentNumber = numbers[rnd.Next(0, numbers.Count)];

    Console.WriteLine(currentNumber);

    numbers.Remove(currentNumber); // remove current random number from list
}

Enumerable.Range(0, 9).ToList() creates a list containing the numbers from 0 to 8. Then in the loop we choose a random number from the list and remove it from the list at the end of the loop, so that the next cycle it can't be chosen again.

Răzvan Flavius Panda
  • 21,730
  • 17
  • 111
  • 169
0

Found this from a web search - Fisher-Yates shuffle, implemented in Perl.

This will generate an unbiased randomization of any input array.

sub fisher_yates_shuffle {
    my $array = shift;
    my $i;
    for ($i = @$array; --$i; ) {
        my $j = int rand ($i+1);
        next if $i == $j;
        @$array[$i,$j] = @$array[$j,$i];
    }
}

For more info:

http://en.wikipedia.org/wiki/Fisher%E2%80%93Yates_shuffle

And the original I found was from:

http://perl.livejournal.com/101830.html

tbh
  • 51
  • 1
  • 5
  • It's more the algorithm than the code. Can't speak for unbiased nature of Random() function in C#, whereas Fisher-Yates definitely is. – tbh Nov 19 '12 at 19:05