Page 1 of 2

"Fair" random number generator

Posted: Sat Aug 31, 2013 3:34 pm
by JaseMourne
In a turn based strategy game where when two opposing units clash, one scores a hit and the other does not, and this is determined by a single attribute (Combat) and a bit of randomness, that randomness has to be as "fair" as possible. An idea crossed my mind when thinking about how to balance the random factor - and this is applicable in any almost game genre, I guess.

When player 1's (P1) unit attacks player 2's (P2) unit, there are two separate dice rolls to add a bit of randomness to the combat, which is otherwise primarily based on their Combat attribute (well, it's not really a dice roll, it's rather a random number from 0 to 1, but let's just use the word for simplicity). Now when P1's roll is greater than P2's roll, we will make P1's next roll weaker, and P2's roll stronger. This repeats forever, so if P1's rolls are still somehow greater three times in a row, the 4th roll will be much weaker, and so on. If then P1's rolls are weaker 3 times in a row, the roll modifiers of both players will even out. Of course, these roll modifiers are set to 1 by default for all players. Based on how strong the roll bonus/penalty is, we can control how much lucky/unlucky a player can get. Good/bad streaks of luck are still possible, but extremely rare.

This roll modifier is always bound to a single player, and each player has their own. So, from a single player's perspective, they should only very very rarely experience a big good/bad luck streak. And the common problem in TBS games where luck plays a factor is that players perceive bad streaks as a very negative thing, and these bad streaks tend to happen. This system should solve it.

What do you think, guys?

Re: "Fair" random number generator

Posted: Sat Aug 31, 2013 3:42 pm
by raidho36
No. There should be no such bias in random function. Even if sounds sweet in theory, in practice it will always backfire by effectively making this random utterly useless. Besides, it's a dice, they're supposed to produce random results, without any bit of fairness to it.

Re: "Fair" random number generator

Posted: Sat Aug 31, 2013 4:13 pm
by vrld
I disagree with raidho: Since humans in general (me included) are not very good at perceiving and understanding random events, an unbiased random draw might be perceived as unfair, for example when the opponent lands 3 critical strikes in a row, while your unit misses every turn. Many (board) games include rules to balance for this. In Monopoly, for example, you go to jail for rolling doubles three times in a row.

Your method seems to be a good compromise between fairness and scalability, but you should play test it to see if it really works. You could also tweak it to just consider the last instead of all rounds.

Another possibility might be what I like to call a random bag: For each unit, you fill a bag (table) with all possible outcomes, maybe with a bias. On each turn, you pick one of the outcomes at random and remove it from the bag. Once the bag is empty, you refill it and repeat the process. You can also refill the bag once it has less than x items in it, to keep things interesting.

Example: The possible outcomes are 'miss', 'hit', 'critical hit'. You have one veteran unit pitted against a novice. The veteran unit's bag is v = {'miss', 'miss', 'hit', 'hit', 'critical hit'} and the novice's bag is n = {'miss', 'miss', 'hit', 'critical hit'}. You refill the bag when it contains less than two items.

Round one: veteran draws 'miss', novice draws 'hit'. the bags now contain: v = {'miss', 'hit', 'hit', 'critical hit'}, n = {'miss', 'miss', 'critical hit'}
Round two: veteran draws 'hit', novice draws 'miss'. the bags now contain: v = {'miss', 'hit', 'critical hit'}, n = {'miss', 'critical hit'}
Round three: veteran draws 'critical hit', novice draws 'miss', and the bag is refilled. the bags now contain: v = {'miss', 'hit'}, n = {'miss', 'miss', 'hit', 'critical hit'}.
Round four: veteran draws 'hit', novice draws 'critical hit'. Novice is dead, so no bags are refilled.

Re: "Fair" random number generator

Posted: Mon Sep 02, 2013 11:29 am
by substitute541
vrld wrote:I

Another possibility might be what I like to call a random bag: For each unit, you fill a bag (table) with all possible outcomes, maybe with a bias. On each turn, you pick one of the outcomes at random and remove it from the bag. Once the bag is empty, you refill it and repeat the process. You can also refill the bag once it has less than x items in it, to keep things interesting.
Reminds me of the "selecting things at random with* replacement from a sample of size n" thingy that I learned from a certain online course.

Edit: it is without, as micha said down below.

Re: "Fair" random number generator

Posted: Mon Sep 02, 2013 11:47 am
by micha
It is without replacement. This is the whole point. By not replacing objects, the number of occurances is distributed more evenly (and also less randomly).

Re: "Fair" random number generator

Posted: Tue Sep 03, 2013 11:49 am
by JaseMourne
raidho36 wrote:No. There should be no such bias in random function. Even if sounds sweet in theory, in practice it will always backfire by effectively making this random utterly useless. Besides, it's a dice, they're supposed to produce random results, without any bit of fairness to it.
To me, that is a question of design, as to how much random combat should get. In my design, I only want a bit of randomness added, so when a unit with a strength of 2 fights a unit with a strength of 1, the latter should never win 0:7, or the like. With an unbiased random function, this does happen (playtested, of course).
vrld wrote:I disagree with raidho: Since humans in general (me included) are not very good at perceiving and understanding random events, an unbiased random draw might be perceived as unfair, for example when the opponent lands 3 critical strikes in a row, while your unit misses every turn. Many (board) games include rules to balance for this. In Monopoly, for example, you go to jail for rolling doubles three times in a row.
Exactly.
Your method seems to be a good compromise between fairness and scalability, but you should play test it to see if it really works. You could also tweak it to just consider the last instead of all rounds.
Yes, it does work, I tested it. It gives results that are more or less expected, with a few peaks here and there. The reason I've posted is because I wanted to know if there are better and/or already known methods of achieving this.
Another possibility might be what I like to call a random bag: For each unit, you fill a bag (table) with all possible outcomes, maybe with a bias. On each turn, you pick one of the outcomes at random and remove it from the bag. Once the bag is empty, you refill it and repeat the process. You can also refill the bag once it has less than x items in it, to keep things interesting.

Example: The possible outcomes are 'miss', 'hit', 'critical hit'. You have one veteran unit pitted against a novice. The veteran unit's bag is v = {'miss', 'miss', 'hit', 'hit', 'critical hit'} and the novice's bag is n = {'miss', 'miss', 'hit', 'critical hit'}. You refill the bag when it contains less than two items.

Round one: veteran draws 'miss', novice draws 'hit'. the bags now contain: v = {'miss', 'hit', 'hit', 'critical hit'}, n = {'miss', 'miss', 'critical hit'}
Round two: veteran draws 'hit', novice draws 'miss'. the bags now contain: v = {'miss', 'hit', 'critical hit'}, n = {'miss', 'critical hit'}
Round three: veteran draws 'critical hit', novice draws 'miss', and the bag is refilled. the bags now contain: v = {'miss', 'hit'}, n = {'miss', 'miss', 'hit', 'critical hit'}.
Round four: veteran draws 'hit', novice draws 'critical hit'. Novice is dead, so no bags are refilled.
Now this is very interesting. Catches my curiosity. Let's see if it's applicable in my design. Gonna churn some numbers now... Thank you. :)

Re: "Fair" random number generator

Posted: Tue Sep 03, 2013 12:52 pm
by vrld
You might also be interested in this article: Probability and Games: Damage Rolls. The article provides a nice (and interactive!) introduction to designing random distributions in games.

Re: "Fair" random number generator

Posted: Tue Sep 03, 2013 1:02 pm
by JaseMourne
Okay, so the "random bag" implementation does not work too well for me. I probably could make it work with some serious effort, though. Nonetheless, I'm glad I've learned about this method. Might come handy in some other situations.
vrld wrote:You might also be interested in this article: Probability and Games: Damage Rolls. The article provides a nice (and interactive!) introduction to designing random distributions in games.
I'm right on it, sir. Thank you. :)

Re: "Fair" random number generator

Posted: Wed Sep 04, 2013 3:26 pm
by timmeh42
It might be interesting to read how Dota 2 implements Pseudo-Random Distribution - as a game with a massive playerbase, it has to strive to make random events as "fair" as possible or suffer the consequences of a large amount of moaning and whining (and less fun-having).

Re: "Fair" random number generator

Posted: Wed Sep 11, 2013 1:17 am
by JaseMourne
timmeh42 wrote:It might be interesting to read how Dota 2 implements Pseudo-Random Distribution - as a game with a massive playerbase, it has to strive to make random events as "fair" as possible or suffer the consequences of a large amount of moaning and whining (and less fun-having).
Thank you for another good link. I'm well aware of that (it's been used in Warcraft 3, too), but that only works for singular effects that either do or do not trigger - these effects are not evaluated against anything else but the chance. So, each effect remembers its own chance of triggering, which goes up every time it does not trigger, and goes down every time it does trigger. As an exercise, some time ago, I've devised a method based on this principle, but much simpler, with very solid results.

Problem is, in my case, you are evaluating two such effects standing against each other. And because unit A and unit B may, but also may not ever clash again after the first clash, you cannot store the effect's chance as a standalone thing. You need to try to assure the "overall fairness", which can only be, in my opinion, be done on a player-to-player basis. That's why I'm shooting for the approach described in OP.