0

I'm trying to program a slot machine.

I have 5 rollers and 7 winning pictures. It looks like

-----|-----|-----|-----|----|

-----|-----|-----|-----|----|

-----|-----|-----|-----|----|

I get each roll 3 pictures.

foreach (var s in Walze1)
        {
            Random rnd = new Random();
            int perCent = rnd.Next(Walze1dot7, 110);

            //10 % Chance auf 7 per Walze
            if (perCent <= 10)
            {
                Walze1dot7 = 11;
                s.Text = "7";
            }
            //10 % Chance auf Glocke per Walze
            else if (perCent <= 20 & perCent > 10)
            {
                s.Text = "Glocke";
            }
            //15 % Chance auf Melone
            else if (perCent <= 35 & perCent > 20)
            {
                s.Text = "Melone";
            }
            //15 % Chance auf Pflaume
            else if (perCent <= 35 & perCent > 50)
            {
                s.Text = "Pflaume";
            }
            //20 % Chance auf Orange
            else if (perCent <= 70 & perCent > 50)
            {
                s.Text = "Orange";
            }
            //20 % Chance auf Zitrone
            else if (perCent <= 90 & perCent > 70)
            {
                s.Text = "Zitrone";
            }
            //20 % Chance auf Kirche
            else if (perCent <= 110 & perCent > 90)
            {
                s.Text = "Kirche";
            }
        }

only one 7 should be possible at one roller.

MY PROBLEM:

I winning too much... the random Code gives me too often a successful picture (min. 3 same pictures for one line).

So how can I change my Code that I will loose more often?

EDIT

It is not a duplicate because i know how to generate a random number...What i need is that i dont get to often a winning pictures (3 each line)...

Let's Say i play with 100 € on 2€ per click. after 50 click i got more than 300 € always.

Maddin
  • 52
  • 9
  • 5
    Possible duplicate of [Random number generator only generating one random number](https://stackoverflow.com/questions/767999/random-number-generator-only-generating-one-random-number) – eye_am_groot Aug 29 '18 at 12:43
  • 3
    I'm guessing you get the same picture multiple times in one line due to the fact that you are creating `rnd` **inside** the `foreach` loop – eye_am_groot Aug 29 '18 at 12:45
  • 2
    The code posted is correct which gives each of the pictures randomly. You should be calling the code multiple times. May be the code that determines the winner is wrong. Also new Random() uses the time of the PC you get the seed for the random generator. What sometimes happens if the function is called multiple times and the computer time hasn't changed to get the same random sequence. So try passing the routine the random sequence and call new Random from parent method so you do not keep on initializing the random number generator. – jdweng Aug 29 '18 at 12:46
  • @Greg sure i creat for each field in the roller a random picture... – Maddin Aug 29 '18 at 12:54
  • 1
    As an aside: I don't think it makes any difference here, but you generally want `&&` (shortcut &) instead of `&` when comparing logical conditions such as these. Although in this case you can likely drop the second half of each test altogether, since it's necessarily true else you wouldn't be here in the `else if` branch. – Rup Aug 29 '18 at 12:54
  • ... except for the pflaume case which will never be true: `else if (perCent <= 35 & perCent > 50)`. You probably meant to swap the numbers. – Rup Aug 29 '18 at 12:55
  • 1
    Greg's and jdweng's point is that you're creating a new `Random` object each time, and there's a chance that these new Random objects will all return the same number (e.g. if they use the current time as the random seed and the current time hasn't changed between loops). Move `Random rnd = new Random();` outside the loop so you reuse the same object. – Rup Aug 29 '18 at 12:57
  • @RUP thanks. Your right i know now how to solve it ! :) – Maddin Aug 29 '18 at 12:58
  • 1
    You actually don't need half of these conditions. I mean, in your first `else if` you have `perCent > 10` which is always guaranteed to be true, because it has passed through the first condition, so you can actually remove the second part of condition everywhere. Just like `if (a < 10) else if (a < 20) else if (a < 35)` etc. – Yeldar Kurmangaliyev Aug 29 '18 at 12:59
  • if you want to loose more, decrease chances for winning image for each slot, or decrease them altogether. – Krzysztof Skowronek Aug 29 '18 at 14:01
  • Remember to coinflip for 'doomed to lose' and 'doomed to win low' before even rolling a random number ;) – Davesoft Aug 29 '18 at 14:53

2 Answers2

0

I didn't test it, but I suggest you can do this:

add using System.Collections.Generic; to your file.

procents are now real procents, the statements are optimized, the Random initialisation is out of the loop, and you store what you rolled.

//sorry for the bad performance, i didn't optimize it.
//you could do that by making a list with the strings in it and remove the one you rolled.
List<string> rolled = new List<string>();
Random rnd = new Random();
foreach (var s in Walze1)
{
    again:
    //generate an number with min 0, max 99
    int perCent = rnd.Next(Walze1dot7, 100);

    //10 % Chance, 0 to 9
    if (perCent < 10)
    {
        s.Text = "7";
    }
    //10 % Chance, 10 to 19
    else if (perCent < 20)
    {
        s.Text = "Glocke";
    }
    //10 % Chance, 20 to 29
    else if (perCent < 30)
    {
        s.Text = "Melone";
    }
    //15 % Chance, 30 to 44
    else if (perCent < 45)
    {
        s.Text = "Pflaume";
    }
    //15 % Chance, 45 to 59
    else if (perCent < 60)
    {
        s.Text = "Orange";
    }
    //20 % Chance, 60 to 79
    else if (perCent < 80)
    {
        s.Text = "Zitrone";
    }
    //20 % Chance, 80 to 99
    else if (perCent < 100)
    {
        s.Text = "Kirche";
    }
    if(rolled.Contains(s.Text)){goto Again;}
    rolled.Add(s.Text);
}
Pang
  • 9,564
  • 146
  • 81
  • 122
Jaapww
  • 1
  • 1
  • Why `if(rolled.Contains(s.Text)){goto Again;}` ? Isn't that deliberately preventing any win? – Rup Sep 13 '18 at 17:50
  • That's preventing to get duplicates. For example, if this roll already contains "Orange", then it rolls again. – Jaapww Sep 18 '18 at 10:35
  • I'm fairly sure that's not the requirement. OP wanted "don't get too often a winning pictures (3 each line)", not 'never get a winning line'. – Rup Sep 18 '18 at 10:39
0

Using (bitwise and)& instead of (logical and) && in your if statements is a problem, but it is not the main one. You should also not generate a new Random() every time you call this function - it is an expensive operation and running it often will slow you down.

You said you tested it, but the randomness was not tested. When you are generating random occurrences you should write a test case that sees how random they really are. In your specific case, you can create a Dictionay<string,int> and initialize it with the strings being every string you can randomly select, and then add 1 to it each time you generate that string.

static Dictionary<string,int> CountUses = new Dictionary<string, int>();

  /* do this once  - so they always print in order*/
        CountUses.Add("", 0);
        CountUses.Add("7", 0);
        CountUses.Add("Glocke", 0);
        CountUses.Add("Melone", 0);
        CountUses.Add("Pflaume", 0);
        CountUses.Add("Orange", 0);
        CountUses.Add("Zitrone", 0);
        CountUses.Add("Kirche", 0);

/* use this in your function */
if (!CountUses.ContainsKey(s.Text))
     CountUses.Add(s.Text, 0);

 CountUses[s.Text]++;

Then call your function 10,000,000 times and see what the numbers look like - they should be fairly close.

    for ( int x = 1; x < 10000000; ++x)
        tester(); //function I made to call your code

    foreach (var key in CountUses.Keys)
            Console.WriteLine(String.Format("{0,10} uses of {1,8} = {2:P}", CountUses[key], key, CountUses[key]/ 10000000.0f));

With your code, the results are not well distributed and sometimes empty:

   1376943 uses of          = 13.77%
    998104 uses of        7 = 9.98%
    937056 uses of   Glocke = 9.37%
   1358398 uses of   Melone = 13.58%
         0 uses of  Pflaume = 0.00%
   1814880 uses of   Orange = 18.15%
   1788699 uses of  Zitrone = 17.89%
   1725919 uses of   Kirche = 17.26%

Replacing & with && is different but still not right (close enough to be random differences):

   1358963 uses of          = 13.59%
   1013747 uses of        7 = 10.14%
    891739 uses of   Glocke = 8.92%
   1382211 uses of   Melone = 13.82%
         0 uses of  Pflaume = 0.00%
   1818295 uses of   Orange = 18.18%
   1825153 uses of  Zitrone = 18.25%
   1709891 uses of   Kirche = 17.10%

With the test code it should be very easy to track down your biggest mistake, and then see if the % you get are actually the ones you expect.

Ves
  • 387
  • 2
  • 10