Sie können einen Algorithmus verwenden, den ich Distributed Probability RNG nenne .
Es sieht aus wie das:
public class Item {}
public class ExampleBucket
{
private List<Item> bucket = new List<Item>();
public void Add (Item item, int count)
{
for (int i = 0; i < count; i++)
{
bucket.Add(item);
}
}
public Item GetRandom (Random rng)
{
var index = rng.Next(0, bucket.Count);
return bucket[index];
}
}
Sie können wie folgt initialisieren:
private void InitBucket()
{
var itemA = new Item();
var itemB = new Item();
var itemC = new Item();
var bucket = new ExampleBucket();
bucket.Add(itemA, 1);
bucket.Add(itemB, 2);
bucket.Add(itemC, 3);
}
Sie können Elemente erhalten, indem Sie GetRandom(Random)
Ihre ExampleBucket
Instanz aufrufen .
Wie funktioniert es?
Wir haben eine Liste bucket
in der ExampleBucket
Klasse benannt. Zunächst einmal ist es leer. Durch Aufrufen der Add(Item, int)
Methode fügen Sie Item
der bucket
Liste eine bestimmte Anzahl von s hinzu .
Am Ende unserer InitBucket()
Methode bucket
sieht die Liste folgendermaßen aus:
itemA // 1 x itemA
itemB // 2 x itemB
itemB
itemC // 3 x itemC
itemC
itemC
Dann generieren wir einfach eine Zufallszahl zwischen 0
und bucket.Count
und geben das Element zurück, das diesem Index in der bucket
Liste entspricht.
Die Wahrscheinlichkeit, ein bestimmtes Element aus einer Liste zu erhalten, beträgt Item Count / Total Count
. Je mehr Elemente eines bestimmten Typs in der Liste enthalten sind, desto größer ist die Wahrscheinlichkeit, dass dieses Element ausgewählt wird.
Also in diesem Fall;
Probability of getting itemA = 1 / (1+2+3)
Probability of getting itemB = 2 / (1+2+3)
Probability of getting itemC = 3 / (1+2+3)
Wenn Sie GetRandom()
100000 Mal laufen (der Test ist hier in Fiddle ), können Sie sehen, dass die Werte den perfekten Ergebnissen ziemlich nahe kommen:
A count = 16690 | Expected = 16666
B count = 33519 | Expected = 33333
C count = 49791 | Expected = 50000
Was mir an diesem Algorithmus am besten gefällt, ist, dass Sie keine Gesamtanzahl von Elementen angeben müssen. Sie können jederzeit einen beliebigen Artikel hinzufügen und müssen sich nicht um den Rest kümmern.
Wenn Sie beispielsweise die Wahrscheinlichkeit erhöhen möchten, itemA
von der Liste zu kommen, können Sie einfach anrufen
bucket.Add (itemA, theAmountYouWant);
und Sie müssen nichts anderes tun.